美文网首页
读书笔记-Swift-03变量和简单类型

读书笔记-Swift-03变量和简单类型

作者: 秋水天的练功房 | 来源:发表于2017-08-26 17:32 被阅读0次

变量就是类似于鞋盒之类的概念,装变量的盒子。所以需要有指定的型号。

变量作用域和生命周期

  • 变量,在定义的地方赋予了这个变量的作用域和生命周期。

  • swift中的变量可以在任何地方定义。按生命周期分为几类:

    • 全局变量。在swift文件的最上一级定义。生命周期和程序生命周期一致。可以被文件内的所有的代码看到。可以被文件外同一模块的代码看到。
    • 属性。 属性是定义在对象类型顶层的变量。有实例属性和类属性之分。
      * 实例属性:每个实例的值不同。生命周期和实例相同。
      * 类属性:前面加static/class。生命周期和对象类型的生命周期相同。
      属性在内对象声明的代码内可见。类属性在类型可见的地方可见。
  • 本地变量。本地变量就是定义在函数体中的变量。在大括号内有效。


变量申明

  • 变量声明用let或var。let声明常量,var声明变量。
  • 变量声明之后,类型是不可以改变的。可以隐式给定类型也可以显示给定类型。隐式给定就是用初始化值的类型给定类型。可以同时指定类型又赋初值。这个有时候是多余的,有时候不是:
    • 有时候swift类型推导会出错。比如用语法量数字的时候,swift默认推导为Int或Double类型,但是我如果想要别的类型的话,就需要制定。
    • 有时候swift推导不出类型来。
    • 程序员推导不出类型来。所以有的时候干脆写上,让自己心里清楚。
  • 因为类型清楚,所以变量可以不初始化。只是声明。但最好别这么干,尤其是本地变量。引用本地没有初始化的变量,编译器会报错。一般在需要条件初始化的时候使用。
  • 变量在作为参数传入函数之前,需要被定义和初始化。即使初始化的值是假的。
  • 有时候,调用一个函数返回一个值。然后在这个函数参数中传入一个函数作为参数,这个作为参数的函数中又用到这个返回值。此时需要先定义这个返回值然后赋值个假的。如果不定义,参数函数中将不能使用。如果不赋初值,也是不能使用的。
  • 对象的属性可以在对象初始化函数中进行赋初值,而不是在声明的时候赋初值。一般都会给出明确的类型。

计算初始化

  • 有时候需要做一些运算才给变量赋初值。这时候最好的办法就是使用匿名函数。然后立刻调用。属性初始化也可以这么干。给属性初始化也就只有这种方式了,毕竟此时实例还没有初始化。

计算变量

  • 变量可以被计算的。也就是说,变量不一定只是一个值,也可以是一个函数。有seter/getter函数。此时变量只能定义为let型。类型也必须明确定义。
  • 使用的时候,和普通变量没有什么区别,只是调用了get、set方法。
  • set方法的默认参数是newValue。也可以设置成别的。
  • 如果没有set方法,那么这个变量就不可更改。get是必须要要有的。如果没有set,那么get可以直接跟在后面。
  • 计算变量有很多应用场景:
    • 设置只读变量
    • 装饰函数
    • 装饰其他变量
  • 计算变量可以引用其他属性。也可以调用实例方法。因为这个方法直到实例存在的时候才会被调用。

Setter观察者

  • 计算变量可以注入函数监控设置值。willSet,didSet。
  • didSet函数可以修改存储变量的值。但是不会调用观察函数,否则就死循环了。
  • 实际编程过程中,经常使用存储变量的观察函数,而不是计算变量。
  • 计算变量没有setter观察者,因为没有必要。

懒初始化

  • 懒初始化的懒不是道德审判。是一种重要的行为。存储变量带着初始值声明,如果采用懒加载的方式,那么直到用到的时候,才会真正计算和赋值变量。
  • 全局变量。是自动懒初始化的。在底层是等同于dispatch_once的。因此是线程安全的的单列。
  • 静态变量。也是自动懒初始化的。和全局变量一样。
  • 实例属性。默认不是懒初始化。如果需要懒初始化,就要用lazy标示。并且必须声明为var类型,不能是let类型。
  • swift3中dispatch_once已经没有了。全局和静态的有这个特性。懒初始化常常用来实现单例模式。
class MyClass {
  static let = sharedSingleton = MyClass()
}
  • 为什么会需要懒加载呢?大部分情况下是因为初始化的值代价很大。还有一种情况是,懒加载可以引用实例的内容。
  • 常常用定义调用函数来初始化懒初始化变量。
lazy var prog : UIprogressView = {
  let p = UIProgressView(progressViewStyle: .default)
  p.xxx = xxx
  ......
  return p
}()
  • 语言也有一些问题。懒属性不能有setter 观察。let变量不能懒加载。不是原子操作,有多线程问题。

内置简单类型

Bool

  • Bool 对象类型只有两个值,true,false。
  • Cocoa中经常有函数返回Bool类型值,表明这个函数执行情况。
  • swift中,没有隐含别的东西表明是true或false,不如C语言中的0或1。
  • Bool类型的操作。(!,&&,||)与或非。

Numbers

  • 大部分情况下,Int和Double就够了。其他类型是为了兼容OC。
  • Int 整形。多大和机器字相关。
  • Int 可以使用各种进制。0b,0o,0x等。
  • Double型。15位小数。默认的语法小数是Double类型。可以用科学计数法标示Double类型。
  • 数字转换。直接函数强转即可。
  • 数字作为参数传入函数时,仅仅会对字面量的数字做隐式转换,确定类型的变化不会做转换。需要自己明确转换。
  • 其他数字类型。主要是和Cocoa兼容的操作。很多时候需要强制类型。
  • 有时候你要赋值的变量类型是什么你也不知道,需要用numbericast()来动态转换。
  • 算术运算。+,-,*,/
  • swift3之后,数字带了各种方便的函数。
  • 数字的比较。

String

  • swift的字符串是非常现代的,内部是Unicode。
  • \u{...}可以拿Unicode码转换成字符串。还有其他转义。 \n 换行 \t tab \" 普通引号 \\普通反斜杠
  • swift字符串最常用的功能是字符串插入。(某对象) 可以输出字符串。当然括号里面的也可以是表达式。
  • 字符串重载了加号。加号是拼接字符串的意思。也可以字符串加数字。都是拼接字符串。重载了 +=,相当于append。
  • 数组可以用joined加上分隔符的方法输出一个带分隔符的字符串。
  • 比较方法 == 也重载了。两个字符串相等。
  • 还有一些比较实用的函数。 isEmpty,hasPrefix(:),hasSuffix(:),uppercase,lowercase。
  • 字符串和Int类型之间的转换是可以的。数字转字符串,直接调用函数,还可以按进制转。
  • 如果是表示数字的字符串,也可以转换为数字。
  • 任何对象都可以转换成字符串,需要遵循三个协议:Streamable, CustomStringConvertible, CustomDebugStringConvertible。
  • 字符串的长度,是字符的长度,不是空间的长度。
  • 你可以一个个遍历字符串中的字符,还可以按编码格式要求。
  • swift语言本身没有类似大小写之类的函数,这些功能都在Foundation中,一般情况下都可以使用。
  • swift中的Stirng和NSString的混用。有时候需要强制转换。

Character

  • character代表着一个单独的unicode字符。
  • 字符类型没有语法字符。需要用类型初始化。

Range

  • range类型标示一组范围。有两种语法形式。前后有空格也是合法的。
    • a...b : 从a到b。包括b。
    • a..<b:从a到b。不包括b。
  • 大部分情况下是Int类型。如果后面那个是负数,那么必须用括号或者空格分开。
  • 没有颠倒的range。起始必须比终点小。如果起点比终点大,编译器不管,但是运行时会挂掉。可以调用reversed方法来逆序。
  • range的端点可以是double类型的。
  • 也有办法检测是否两个range重叠,包含等。
  • range另一个应用是索引序列。
let s = "hello"
let arr = Array(s.characters)
let result = arr[1...3]
let s2 = String(result) //"ell"
  • swift的string可以配合range做各种操作
  • swift的range类型和NSRange是完全不同的结构。但是可以相互转换。

Tuple

  • 元组是轻量级的可变有序集合。
 var pair : (Int, String)
  • 类型可以推导的话,就可以不用明确给出了。
  • 元组是swift特有的语法,OC中没有,所以要在OC看不到的地方使用。
  • 元组可以用作函数返回多个值。
  • 元组可以直接引用其中的元素,可以用序号来引用。
  • 元组也可以带标签,用标签来标示。带标签的不带标签的可以相互赋值。
  • 可以用typealias来给元组命名,方便使用。
  • Void返回值,实际上是返回一个空的元组()

Optional

  • Optional类型是个枚举。包了个其他类型。之所以是option,是说他可能是某种类型的值,也可能不是。

  • Optional初始化后成为某一类型之后,就不能变了。只能是包这一类型的东西。

    var stringMaybe = Optional("abcd")
    stringMaybe = Optional(123) // compile error
    
  • Optional类型对swift非常重要,以至于嵌入进语言内部了。

  • Optional通常都不是初始化的方式使用它,而是赋值的方式使用。

var stringMaybe = Potional("howdy")
stringMaybe = "farewell"//看似类型不匹配,但这是可以的的,合法的。
  • 语法糖。类型后面加个问号,表示是optional类型的。
  • 函数参数需要传入一个optional类型的。可以直接传入optional类型包含的类型。因为传参数就类似赋值。在函数内部,还是一个optional类型。
  • 反过来则不行。如果你想用optional中的具体类型,你就需要解包。
  • 可以强制解包。在optional类型后面加个感叹号。
  • 隐式解包optional。隐式解包的optional类型依然是optional类型。只是让编译器帮你更方便。就是告诉编译器,如果optional用到包含类型的地方,帮忙解一下。
String?  普通的optional类型
String!   隐含解包的optional类型
  • 隐式解包的optional类型不是一个独立的类型,仅仅是optional类型做了一些特殊的标记。
  • nil关键词。一个optional类型不包含任何类型,怎么办?可以和nil做比较,然后判定。
  • optional是唯一可以隐式初始化为nil的类型。其他的类型,没有初始化是不能使用的。编译报错。
  • 不能解包一个为nil的optional。否则会crash。

相关文章

  • 读书笔记-Swift-03变量和简单类型

    变量就是类似于鞋盒之类的概念,装变量的盒子。所以需要有指定的型号。 变量作用域和生命周期 变量,在定义的地方赋予了...

  • 第二章

    变量和简单类型 单行注释和多行注释 Python是弱类型语言 Python变量的特征 Python变量命名规则 P...

  • javascript高级程序设计 读书笔记

    读书笔记 基本概念 语法 变量 数据类型 undefined类型 null类型 number类型 String类型

  • javascript堆和栈

    javascript变量类型分为基本类型和引用类型 栈 stack”和“堆 heap” 简单的来讲,stack上分...

  • 简单数据类型和复杂数据类型

    简单数据类型和复杂数据类型 1.1 简单数据类型 ​ 简单类型(基本数据类型、值类型):在存储时变量中存储的是值本...

  • JavaScript 变量类型

    变量类型 JavaScript 中的变量类型分为值类型(又称为简单类型、基本数据类型)以及引用类型。 【值类型】:...

  • c#基础

    1.值类型和引用类型的区别 I.简单比较: 值类型的变量直接存储数据,引用类型的变量持有的是数据的引用,...

  • 变量、作用域和内存问题

    一、变量 1、变量可能包含两种不同数据类型的值:基本类型值和引用类型值。基本类型值指的是 简单的数据段,而引用类型...

  • Python入门语法综述

    1.变量和简单数据类型 1.变量 message = "hello world python" print(mes...

  • python变量和简单的数据类型

    python第一课:变量和简单的数据类型

网友评论

      本文标题:读书笔记-Swift-03变量和简单类型

      本文链接:https://www.haomeiwen.com/subject/vgcvdxtx.html