DAY11:Classes and Structures

类是引用类型

与值的类型不同,引用类型被赋予到一个变量,常量或者被传递到一个函数时,其值不会被拷贝,因此,引用的是存在的的实例本身不是其拷贝。

let tenEight = VideoMode()
tenEight.resolution = hd
tenEight.interlaced = true
tenEight.name = "1080i"
tenEight.frameRate = 25.0

let alsoTenEight = tenEight
alsoTenEight.frameRate = 30.0
print("The frameRate property of tenEight is now \(tenEight.frameRate)")
//The frameRate property of tenEight is now 30.0"

声明了一个名为tenEight的常量,引用的是VideoMode的新实例。tenEight被赋予名为alsoTenEight的新常量,同时对alsoTenEight的frameRate进行修改,我们可以看见tenEight的frameRate也被修改了,这说明了tenEight和alsoTenEight实际上引用的是相同的VideoMode实例,换句话说这是同一个实例的两种叫法。

注意:
我们可以看见这两个 tenEight,alsoTenEight被声明的是常量而不是变量,但是我们依然可以改变alsoTenEight.frameRate的值,这是因为tenEight和alsoTenEight这两个常量的值并没有改变,他们并不“存储”这个VideoMode实例,而仅仅是对VideoMode的引用,所以改变的十被引用的VideoMode的frameRate的属性,不是引用VideoMode的常量的值。

总结

也就是说枚举和结构体是值类型,我们修改了其值,其他被传递给的变量、常量、函数值不会变化,因为是对那个值的拷贝;类是引用类型,我们修改了一处,其他引用同一个实例的地方,都会相应的变化

恒等运算符

swift中内建了两个恒等运算符,用来检测两个常量或者变量是否引用同一个实例:

  1. 等价于(===)
  2. 不等价于(!==)
    if tenEight === alsoTenEight {
        println("tenEight and alsoTenEight refer to the same Resolution instance.") 
    }
    //打印出tenEight and alsoTenEight refer to the same Resolution instance.

类和结构体的选择

结构体实例总是通过值传递,类的实例是通过类的引用传递,两者的运用场景是不同的,按照通用的准则,当符合一条或者多条的时候请选择结构体:

  • 该数据结构的主要目的是用来封装少量的相关的简单数据
  • 有理由预计该数据结构的实例在被赋值的时候或者传递的时候,封装的数据将会被拷贝而不是被引用
  • 该数据结构中存储的值类型属性,应用该被拷贝,而不是被引用。
  • 该数据结构不需要继承另一个既有类型的属性或者行为

字符串(String)、数组(Array)、和字典(Dictionary)类型的赋值与复制行为

swift中,许多基本类型,比如String,Array,Dictonary类型均以结构体的形式实现,这意味着被赋值给新的常量或者变量,或者被传入函数或者方法中时,他们的值被拷贝。
Object-C中的NSString、NSArray和NSDictionary类型都是以类的形式实现的,所以他们在被赋值或者被传入函数或者方法的时候,不会发生拷贝,而是传递现有实例的引用。

你可能感兴趣的:(DAY11:Classes and Structures)