Swift 学习笔记

Swift -- 构造过程

2017-06-19  本文已影响8人  GY1994

构造过程是使用类、结构体或枚举类型的实例之前的准备过程。在新实例可用前必须执行这个过程,具体操作包括设置实例中每个存储属性的初始值和执行其他必须的设置或初始化工作。

存储属性的初始赋值

类和结构体在创建实例时,必须为所有存储型属性设置合适的初始值。存储型属性的值不能处于一个未知的状态。
注意:当你为存储型属性设置默认值或者在构造器中为其赋值时,它们的值是被直接设置的,不会触发任何属性观察者。

init(){
    //在此处执行构造过程
}

自定义构造过程

struct A {
    var num : Double;
    init(value : Double) {
        num = value;
    }
    init(newValue : Double) {
        num = newValue * 2;
    }
}
let a = A(value: 10);//num值为10;
let b = A(newValue: 10);//num值为20
struct A {
    var num : Double;
    init(_ value : Double) {
        //隐藏外部名
        num = value;
    }
    init(out newValue : Double) {
        //out为外部名
        num = newValue * 2;
    }
}
let a = A(10);//num值为10;
let b = A(out: 10);//num值为20
class myclass{
      var text: String
     var response: String?
     init(text: String) {
         self.text = text
     }
     func ask() {
         print(text)
     }
}
let my = myclass(text: "geyang");
my.ask();

我们将属性response声明为String?类型,或者说是可选字符串类型,当myclass实例化时,它将自动赋值为nil,表明此字符串暂时还没有值。

默认构造器

如果结构体或类的所有属性都有默认值,同事没有自定义的构造器,那么Swift会给这些结构体或类提供一个默认构造器。这个默认构造器将简单地创建一个所有属性都设置默认值得实例。

class myclass{
    var text: String = "how old are you";
    var response: String?
}
let my = myclass();//默认构造器

由于该类中的所有属性都有默认值,且它是没有父类的基类,它将自动获得一个为所有属性设置默认值得默认构造器。

类的继承和构造过程

init(paramters){
      statements;
}

便利构造器也采用相同样式的写法,但需要在init关键字之前防止convenience关键字,并使用空格将它们俩分开:

convenience init (paramter){
      statements;
}
//便利构造器
class A{
    var a : Int;
    var b : Int;
    //便利构造器
    convenience init(b : Int){
        self.init(a: 0, b: b);
    }
    //指定构造器
    init(a : Int, b : Int) {
        self.a = a;
        self.b = b;
        print("class ab init!");
    }
}

可失败的构造器

如果一个类,结构体或枚举类型的对象,在构造过程中有可能失败,则为定义一个可失败的构造器,这里所指的“失败”是指,如给构造器传入无效的参数值,或缺少某种所需的外部资源,又或是不满足某种必要的条件等。
为了妥善处理这种构造过程中可能会失败的情况,你可以在一个类,结构体或枚举类型定义中,添加一个或多个可失败构造器,其语法为init关键字后面添加问号(init?)。
可失败构造器会创建一个类型为自身类型的可选类型的对象,你通过return nil语句来表明可失败构造器在何种情况下“失败”。

struct Animal {
     let species: String
     init?(species: String) {
         if species.isEmpty { return nil }
         self.species = species
     }
}

定义了一个名为 Animal 的结构体,其中有一个名为 speciesString 类型的常量属性。同时该结构体 还定义了一个接受一个名为 species 的 String 类型参数的可失败构造器。这个可失败构造器检查传入的参数是否 为一个空字符串。如果为空字符串,则构造失败。否则,species 属性被赋值,构造成功。

必要构造器

在类的构造器前添加required修饰符表明所有该类别的子类都必须实现构造器

class SomeClass{
      required init(){
      }
}

在子类重写父类的必要构造器时,必须在子类的构造器前也添加 required修饰符,表明该构造器要求也应用于继承链后面的子类。在重写父类中必要的指定构造器时,不需要添加 override修饰符。

通过闭包或函数设置属性的默认值

如果某个存储型属性的默认值需要一些定制或设置,你可以使用闭包或全局函数为其提供定制的默认值。每当某
个属性所在类型的新实例被创建时,对应的闭包或函数会被调用,而它们的返回值会当做默认值赋值给这个属
性。
这种类型的闭包或函数通常会创建一个跟属性类型相同的临时变量,然后修改它的值以满足预期的初始状态,最
后返回这个临时变量,作为属性的默认值。

class SomeClass {
    let someProperty: SomeType = {
    // 在这个闭包中给 someProperty 创建 一个默认值 
   // someValue 必须和 SomeType 类型相同
    return someValue
}() 
}

注意闭包结尾的大括号后面接了一对空的小括号。这用来告诉 Swift 立即执行此闭包。如果你忽略了这对括 号,相当于将闭包本身作为值赋值给了属性,而不是将闭包的返回值赋值给属性。

上一篇 下一篇

猜你喜欢

热点阅读