设为首页 加入收藏

TOP

【Swift学习】Swift编程之旅---构造方法(十八)(二)
2017-10-13 10:29:18 】 浏览:6512
Tags:Swift 学习 编程 之旅 --- 构造 方法 十八
盖上面所说的默认行为。

struct Celsius { var temperatureInCelsius: Double init(fromFahrenheit fahrenheit: Double) { temperatureInCelsius = (fahrenheit - 32.0) / 1.8 } init(fromKelvin kelvin: Double) { temperatureInCelsius = kelvin - 273.15 } init(_ celsius: Double) { temperatureInCelsius = celsius } } let bodyTemperature = Celsius(37.0) // bodyTemperature.temperatureInCelsius is 37.0

 

 
  可选属性类型
如果你定制的类型包含一个逻辑上允许取值为空的存储型属性--不管是因为它无法在初始化时赋值,还是因为它可以在之后某个时间点可以赋值为空--你都需要将它定义为可选类型optional type。可选类型的属性将自动初始化为空nil,表示这个属性是故意在初始化时设置为空的。
下面例子中定义了类SurveyQuestion,它包含一个可选字符串属性response
class SurveyQuestion { var text: String var response: String? init(text: String) { self.text = text } func ask() { println(text) } } let cheeseQuestion = SurveyQuestion(text: "Do you like cheese?") cheeseQuestion.ask() // 输出 "Do you like cheese?" 
cheeseQuestion.response = "Yes, I do like cheese. 

 

调查问题在问题提出之后,我们才能得到回答。所以我们将属性回答response声明为String?类型,或者说是可选字符串类型optional String。当SurveyQuestion实例化时,它将自动赋值为空nil,表明暂时还不存在此字符串。
 
  构造过程中常量属性的赋值
只要在构造过程结束前常量的值能确定,你可以在构造过程中的任意时间点修改常量属性的值。
 
注意:对某个类实例来说,它的常量属性只能在定义它的类的构造过程中修改;不能在子类中修改。
 
你可以修改上面的SurveyQuestion示例,用常量属性替代变量属性text,指明问题内容text在其创建之后不会再被修改。尽管text属性现在是常量,我们仍然可以在其类的构造器中修改它的值
class SurveyQuestion { let text: String var response: String? init(text: String) { self.text = text } func ask() { println(text) } } let beetsQuestion = SurveyQuestion(text: "How about beets?") beetsQuestion.ask() // 输出 "How about beets?" 
beetsQuestion.response = "I also like beets. (But not with cheese.) 

 

   默认构造器
Swift 将为所有属性已提供默认值的且自身没有定义任何构造器的结构体或基类,提供一个默认的构造器。这个默认构造器将简单的创建一个所有属性值都设置为默认值的实例。
 
下面例子中创建了一个类ShoppingListItem,它封装了购物清单中的某一项的属性:名字(name)、数量(quantity)和购买状态 purchase state。
class ShoppingListItem { var name: String? 
    var quantity = 1 
    var purchased = false } var item = ShoppingListItem() 

 

由于ShoppingListItem类中的所有属性都有默认值,且它是没有父类的基类,它将自动获得一个可以为所有属性设置默认值的默认构造器(尽管代码中没有显式为name属性设置默认值,但由于name是可选字符串类型,它将默认设置为nil)。上面例子中使用默认构造器创造了一个ShoppingListItem类的实例(使用ShoppingListItem()形式的构造器语法),并将其赋值给变量item。
 
  结构体的逐一成员构造器
除上面提到的默认构造器,如果结构体对所有存储型属性提供了默认值且自身没有提供定制的构造器,它们能自动获得一个逐一成员构造器。
 
逐一成员构造器是用来初始化结构体新实例里成员属性的快捷方法。我们在调用逐一成员构造器时,通过与成员属性名相同的参数名进行传值来完成对成员属性的初始赋值。
 
下面例子中定义了一个结构体Size,它包含两个属性width和height。Swift 可以根据这两个属性的初始赋值0.0自动推导出它们的类型Double。
 
由于这两个存储型属性都有默认值,结构体Size自动获得了一个逐一成员构造器 init(width:height:)。 你可以用它来为Size创建新的实例:
struct Size { var width = 0.0, height = 0.0 } let twoByTwo = Size(width: 2.0, height: 2.0) 

 

  值类型的构造器代理
构造器可以通过调用其它构造器来完成实例的部分构造过程。这一过程称为构造器代理,它能减少多个构造器间的代码重复。
 
构造器代理的实现规则和形式在值类型和类类型中有所不同。值类型(结构体和枚举类型)不支持继承,所以构造器代理的过程相对简单,因为它们只能代理任务给本身提供的其它构造器。类则不同,它可以继承自其它类(请参考继承),这意味着类有责任保证其所有继承的存储型属性在构造时也能正确的初始化。
 
对于值类型,你可以使用self.init在自定义的构造器中引用其它的属于相同值类型的构造器。并且你只能在构造器内部调用self.init。
 
注意,如果你为某个值类型定义了一个定制的构造器,你将无法访问到默认构造器(如果是结构体,则无法访问逐一对象构造器)。这个限制可以防止你在为值类型定义了一个更复杂的,完成了重要准备构造器之后,别人还是错误的使用了那个自动生成的构造器。
 
注意:假如你想通过默认构造器、逐一对象构造器以及你自己定制的构造器为值类型创建实例,我们建议你将自己定制的构造器写到扩展(extension)中,而不是跟值类型定义混在一起。
 
下面例子将定义一个结构体Rect,用来展现几何矩形。这
首页 上一页 1 2 3 4 5 6 下一页 尾页 2/6/6
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
上一篇swift3.0的改变 下一篇FMDB基本使用

最新文章

热门文章

Hot 文章

Python

C 语言

C++基础

大数据基础

linux编程基础

C/C++面试题目