Swift2.0語言教程之類的屬性

Swift2.0語言教程之類的屬性

雖然函數能夠簡化代碼,可是當一個程序中出現成百上千的函數和變量時,代碼仍是會顯得很混亂。爲此,人們又引入了新的類型——類。它是人們構建代碼所用的一種通用、靈活的構造方式。本章將主要詳細講解類的使用。swift

Swift2.0語言的類與對象

類是一種新的數據類型,相似於生活中犬類、貓類等等。而對象則是將這個抽象的類進行了具體化。例如,在犬類中,有哈士奇,金毛等等,這些就是犬類的具體化,即對象。本節將講解類的建立以及如何將類進行具體化(即實例化)爲對象。ide

Swift2.0語言中類的組成

在一個類中一般能夠包含如圖8.1所示的內容。函數

8.1  類的構成工具

其中,這些內容的功能以下:spa

  • q  屬性:它將值和特定的類關聯。.net

  • q  下標腳本:訪問對象、集合等的快捷方式。調試

  • q  方法:實現某一特定的功能,相似於函數。code

Swift2.0語言中建立類

Swift中類的建立要比在Objective-C中簡單的多。在Objecttive-C中,須要使用須要@interface @end 對類中的內容進行聲明,還須要使用@implementation@end 對類聲明的內容進行實現。在Xcode 6.3以前,它們須要放置在不一樣的文件中。雖然在Xcode 6.4中,它們能夠放置在一個文件中,可是也至關的麻煩。Swift語言推出了本身建立類的方式,只使用一個class關鍵字,其通常的建立形式以下:orm

  • class 類名{server

  •   //具體內容

  • }

注意:在類中能夠定義屬性和方法,這些內容會在後面作詳細的介紹。類名可使用「大駱駝拼寫法」方式來命名(如SomeClass),以便符合標準Swift 類型的大寫命名風格(如StringIntBool)。對於後面所講的對象、屬性以及方法等可使用「小駱駝拼寫法」來命名。

【示例8-1】如下建立一個名爲NewClass的類。代碼以下:

  • class NewClass{

  •  

  • }

該類名稱爲NewClass。因爲其中沒有屬性和方法,因此它只是一個空類。

Swift2.0語言實例化對象

實例化對象也能夠稱爲類的實例,其語法形式以下:

  • var/let 對象名=類名()

【示例8-2】如下會建立一個類名爲NewClass的類,而後再進行實例化。代碼以下:

  • import Foundation

  • class NewClass{

  •    

  • }

  • let newClass=NewClass ()

注意:在進行實例化時,類名後必定要加上()。不然程序就會錯誤,如如下的代碼:

  • var newClass = NewClass

因爲在實例化時缺乏了(),致使程序出現如下的錯誤信息:

  • Expected member name or constructor call after type name

以上所講的這些只是簡單的實例化對象。它使用了最簡單的構造器來生成一個對象。在後面的章節中咱們會爲開發者講解構造器的具體用法。

屬性

Objective-C中,屬性是使用關鍵字@property關鍵字進行聲明的內容。在Swift中,屬性能夠將值跟特定的類、結構或枚舉關聯。屬性通常分爲存儲屬性、計算屬性和類型屬性。本節將講解對這些屬性作詳細的講解。

Swift2.0語言存儲屬性

存儲屬性就是存儲特定類中的一個常量或者變量。根據數據是否可變,分爲常量存儲屬性和變量存儲屬性。

1.定義存儲屬性

常量存儲屬性使用let關鍵字定義(聲明定義在一塊兒進行,爲了方便稱爲定義),其語法形式以下:

  • let 常量存儲屬性名:數據類型=初始值

變量存儲屬性可使用var關鍵字定義,其語法形式以下:

  • var 變量存儲屬性名:數據類型=初始值

【示例8-3】如下代碼定義類NewClass1,其中包含兩個屬性value1value2,代碼以下:

  • class NewClass1 {

  •     let value1=20

  •     var value2:Int=10

  • }

其中,value1使用let定義爲常量存儲屬性,value2使用var定義爲變量存儲屬性。在定義存儲屬性時,初始值是必不可少的,不然,就會出現錯誤。例如,如下的代碼:

  • class NewClass1 {

  •     let value1=20

  •     var value2:Int

  • }

在此代碼中,因爲value2後面未加初始值,致使程序出現如下的錯誤信息:

  • Class 'NewClass1' has no initializers

2.訪問存儲屬性

對於這些存儲屬性的訪問,須要使用「.」點運算符。其語法形式以下:

  • 對象名.常量存儲屬性名/變量存儲屬性名

【示例8-4】如下定義了3個存儲屬性firstValuesecondValuethirdValue,而後進行訪問。代碼以下:

  • import Foundation

  • class NewClass{

  •     let firstValue:Int = 0

  •     let secondValue=200

  •     var thirdValue:String="Hello"

  • }

  • let newclass=NewClass()

  • //存儲屬性的訪問

  • print("firstValue=\(newclass.firstValue)")

  • print("secondValue=\(newclass.secondValue)")

  • print("thirdValue=\(newclass.thirdValue)")

運行結果以下所示:

  • firstValue=0

  • secondValue=200

  • thirdValue=Hello

注意:對存儲屬性進行訪問時,只能夠對在本身類中定義的存儲屬性進行訪問,不然就會出現錯誤,代碼以下:

  • import Foundation

  • class NewClass1 {

  •    var class1Value=10

  • }

  • class NewClass2 {

  •     var class2Value=10

  • }

  • let newclass1=NewClass1()

  • print(newclass1.class1Value)

  • print(newclass1.class2Value)

在此代碼中,因爲class2Value存儲屬性是在NewClass2類中定義的,而不是NewClass1中定義的,因此程序就會出現如下的錯誤信息:

  • 'NewClass1' does not have a member named 'class2Value'

存儲屬性除了可使用「.」點運算符進行讀取外,還能夠對其進行修改。修存儲改屬性的通常語法形式以下:

  • 對象名.存儲屬性=修改的內容

【示例8-5】如下代碼就將secondValue的屬性值"Hello"修改成了"Swift",代碼以下:

  • import Foundation

  • class NewClass{

  •     var secondValue:String="Hello"

  • }

  • let newclass=NewClass()

  • print("修改前:secondValue=\(newclass.secondValue)")

  • newclass.secondValue="Swift"                                                                       //修改存儲實現

  • print("修改後:secondValue=\(newclass.secondValue)")

運行結果以下所示:

  • 修改前:secondValue=Hello

  • 修改後:secondValue=Swift

注意:只有變量存儲屬性才能夠進行屬性修改,常量存儲屬性不能夠進行屬性修改。如如下的代碼:

  • import Foundation

  • class NewClass{

  •     let firstValue:Int = 0

  • }

  • let newclass=NewClass()

  • print("修改前:firstValue=\(newclass.firstValue)")

  • newclass.firstValue=100                                                                 //試圖對屬性firstValue的值進行修改

  • print("修改後:\(newclass.firstValue)")

因爲在類中使用了let對存儲屬性進行了定義,其值是不能夠進行修改的,因此出現瞭如下的錯誤信息:

  • annot assign to 'let' property 'firstValue'

3.延遲存儲屬性

若是開發者只有在第一次調用存儲屬性時才能肯定初始值,這時須要使用延遲存儲屬性實現。它的定義通常須要使用關鍵字lazy實現的,其語法形式以下:

  • lazy var 屬性名:數據類型=初始內容

注意:在延遲存儲屬性中初始內容是不能夠省去的。數據類型也是能夠省去的,由於swift會根據初始內容自行判斷數據類型。

【示例8-6】如下將使用lazy來定義一個延遲存儲屬性importer,代碼以下:

  • import Foundation

  • class DataImporter {

  •     var fileName = 123456

  • }

  • class DataManager {

  •     lazy var importer = DataImporter()

  •     var data = [String]()

  • }

  • let manager = DataManager()

  • manager.data += ["Some more data"]

  • print(manager.data)

  • print(manager.importer.fileName)

在沒有調用manager.importer.fileName時,實例的 importer屬性尚未被建立。運行結果以下所示:

  • [Some more data]

  • 123456

咱們可使用斷點調試的方法對此代碼進行調試,來查看它的運行結果。具體步驟以下:

1)爲幾行關鍵代碼添加斷點,並再添加一行代碼,來查看添加importer的值,如圖8.2所示。

8.2  添加斷點

2)單擊運行按鈕,此時會在第一個斷點處出現一個藍色的箭頭,表示此行代碼在運行。而後選擇Debug|Continue命令,按下調試窗口工具欄中的Continue program execution按鈕,查看程序的執行,其中,可使用查看器來觀察屬性值的變化。屬性查看器位於調試信息窗口左半部分,如圖8.3所示。程序的執行,如圖8.4所示。其中,看到的selfdataimporter.storage(由於importer是延遲屬性,爲了和其餘屬性區分,因此在查看器上看到是importer.storage)等都是屬性。它們會隨程序的執行爲改變。

8.3  查看器位置

8.4  調試

在此圖中程序執行到第3步,也就是第三個圖時,類DataManager的屬性data初始化,但沒有給importer.storage屬性進行初始化,一直爲nil,直到執行到第7步,即第7個圖時,才爲importer.storage屬性的屬性初始化。

在定義一個延遲存儲屬性時須要注意如下2點,

1)定義一個延遲存儲屬性時除了lazy外,還須要使用var關鍵字,可是不能使用let關鍵字,不然程序就會出現錯誤,如如下代碼:

  • class DataImporter {

  •     var fileName = 123456

  • }

  • class DataManager {

  •     lazy let importer = DataImporter()

  •     var data = [String]()

  • }

因爲在定義延遲屬性時使用了let關鍵字,因此致使程序出現瞭如下的錯誤:

  • 'lazy' cannot be used on a let

2)初始內容是不能夠省去的,不然程序就會出現錯誤,如如下的代碼,定義了一個沒有初始值的延遲屬性。代碼以下:

  • class DataManager {

  •     lazy var value:Int

  • }

因爲在此代碼中沒有爲value指定初始值,致使程序出現瞭如下的錯誤:

  • lazy properties must have an initializer

計算屬性

除了存儲屬性外,類中還能夠定義計算屬性。計算屬性不存儲值,而是提供了一個gettersetter來分別進行獲取值和設置其餘屬性的值。getter使用get關鍵字進行定義,其通常形式以下:

  • get{

  •   

  •   return 某一屬性值

  • }

  • setter使用set關鍵字進行定義,其通常語法形式以下:

  • set(參數名稱){

  •   

  •   屬性值=某一個值

  •   

  • }

固然,它也能夠沒有參數名稱。這種狀況會後面的內容中講解。在計算屬性中同時包含了gettersetter,其通常定義形式以下:

  • var 屬性名:數據類型{

  •          get{

  •                  

  •                  return 某一屬性值

  • }

  •          set(參數名稱){

  •                  

  •                  屬性值=某一個值

  •                  

  •     }

  • }

【示例8-7】如下代碼定義了一個類WalletClass,用來保存錢包中的金額,其默認單位爲美圓。爲了方便用戶以人民幣爲單位進行訪問值和設置值,因此使用了計算屬性cal。代碼以下:

  • import Foundation

  • class WalletClass{

  •     var money=0.0

  •     var cal:Double{                                                                                        //定義計算屬性cal

  •         get{                                                                                            //定義getter

  •             let RMB=money*6.1

  •             return RMB                                                                  //返回以人民幣爲單位的金額

  •         }

  •         set(RMB){                                                                                 //定義setter

  •             money=RMB/6.1                                                         //返回以美圓爲單位的金額

  •         }

  •     }

  • }

  • var mywallet=WalletClass()

  • mywallet.cal=(20)

  • //輸出

  • print(mywallet.cal)

  • print(mywallet.money)

運行結果以下所示:

  • 20.0

  • 3.27868852459016

注意:在使用計算屬性時須要注意如下三點:

1.定義計算屬性的關鍵字

在定義一個計算屬性時,必須且只能使用var關鍵字,不然就會出現錯誤。如下的代碼,將示例8-7的代碼作了一些修改,代碼以下:

  • class WalletClass{

  •     var money=0.0

  •     let cal:Double{

  •         get{

  •             var RMB=money*6.1

  •             return RMB

  •         }

  •         set(RMB){

  •             money=RMB/6.1

  •         }

  •     }

  • }

在此代碼中定義一個計算屬性,可是使用了let關鍵字,致使程序出現瞭如下的錯誤:

  • 'let' declarations cannot be a computed property

2.數據類型

在定義計算屬性時,必定要爲屬性指定一個明確的數據類型,不然就會出現錯誤提示。例如如下的代碼,是將示例8-7中的代碼作了一些修改。代碼以下:

  • class WalletClass{

  •     var money=0.0

  •     var cal{                                                                                                   //沒有設置cal的數據類型

  •         get{

  •             var RMB=money*6.1

  •             return RMB

  •         }

  •         set(RMB){

  •             money=RMB/6.1

  •         }

  •     }

  • }

在此代碼中因爲沒有爲計算屬性指定一個明確的數據類型,致使程序出現瞭如下的錯誤信息:

  • Computed property must have an explicit type

  • Type annotation missing in pattern

3.set後面的參數類型

在使用計算屬性時,set後面的參數類型要和返回值的類型相同,不須要再指定類型。不然,程序就會出現錯誤。如如下的代碼,此代碼是將示例8-7中的代碼作了一下修改,代碼以下:

  • class WalletClass{

  •     var money=0.0

  •     var cal:Double{                                                                                               //沒有設置cal的數據類型

  •         get{

  •             var RMB=money*6.1

  •             return RMB

  •         }

  •         set(RMB:String){                                                                         //爲參數定義了數據類型

  •             money=RMB/6.1

  •         }

  •     }

  • }

在此代碼中,對set後面的參數RMB指定了數據類型,致使程序出現瞭如下的錯誤:

  • Expected ')' after setter value name

  • Expected '{' to start setter definition

4.沒有定義參數名稱

若是計算屬性的setter沒有定義表示新值的參數名,則可使用默認名稱newValue

【示例8-8】如下代碼就使用了newValue來實現了華氏溫度和攝氏溫度的轉換。代碼以下:

  • import Foundation

  • class DegreeClass{

  •     var degree=0.0

  •     var cal :Double{

  •         get{

  •             let centigradedegree=(degree-32)/1.8

  •             return centigradedegree

  •         }

  •         set{

  •             degree=1.8*newValue+32                                                 //沒有定義參數名稱,可使用默認的

  •         }

  •     }

  • }

  • var degreeClass=DegreeClass()

  • degreeClass.cal=(10.0)

  • print(degreeClass.cal)

  • print(degreeClass.degree)

運行結果以下所示:

  • 10.0

  • 50.0

4.定義參數名後不能使用默認參數名

set後面若是定義了參數名稱,就不能再使用Swift默認的參數名稱newValue。不然,就會致使程序出現錯誤。如如下的代碼,將示例8-8作了一些修改,代碼以下:

  • import Foundation

  • class DegreeClass{

  •     var degree=0.0

  •     var cal :Double{

  •         get{

  •             let centigradedegree=(degree-32)/1.8

  •             return centigradedegree

  •         }

  •         set(aaa){                                                                                                           //定義參數名稱後,使用默認參數

  •             degree=1.8*newValue+32

  •         }

  •     }

  • }

在此代碼中,set後面定義了參數名稱,可是又使用了默認的參數名稱,致使程序出現瞭如下的錯誤:

  • Use of unresolved identifier 'newValue'

5.settergetter的省略

在計算屬性中,若是隻有一個getter,則稱爲只讀計算屬性。只讀計算屬性能夠返回一個值,但不能設置新的值。

【示例8-9】如下將經過getter來獲取名稱的字符串。代碼以下:

  • import Foundation

  • class PersonName{

  •     var name:String=""

  •     var returnName :String{

  •         if (name.isEmpty) {

  •             return "NULL"

  •         }else{

  •             return name

  •         }

  •     }

  • }

  • var personClass=PersonName()

  • print("沒有名字時\(personClass.returnName)")

  • personClass.name=("Tom")

  • print("有名字時\(personClass.returnName)")

在此代碼中,當剛建立實例PersonName後,就去訪問returnName。因爲name默認爲空,因此會返回字符串"NULL"。再對name賦值後,再一次訪問returnName。因爲name不爲空,因此會返回name的內容。運行結果以下所示:

  • 沒有名字時NULL

  • 有名字時Tom

注意:1.在只讀計算屬性中,能夠將get關鍵字和花括號去掉。2.C#等其餘語言中能夠將屬性分爲只讀屬性(只有getter)、只寫屬性(只有setter)和可讀可寫屬性。可是在Swift中就不一樣了,只有只讀計算屬性和可讀可寫計算屬性兩個。沒有隻寫計算屬性,不然程序就會出現錯誤,如如下的代碼:

  • class PersonName{

  •     var name:String=""

  •     var setName :String{

  •         set{

  •             

  •         }

  • }

在此代碼中定義了一個只寫計算屬性,致使程序出現瞭如下的錯誤:

  • Variable with a setter must also have a getter

Swift2.0語言的類型屬性

類型屬性就是不須要對類進行實例化就可使用的屬性。它須要使用關鍵字class進行定義,其定義形式以下:

  • class var 類型屬性名:數據類型{

  •    

  •    返回一個值

  • }

例以下面代碼定義了一個類型屬性count,代碼以下:

  • class var count:Int{

  • return 20

  • }

類型屬性也是能夠被訪問的,其訪問類型屬性的通常形式以下:

  • 類名.類型屬性

【示例8-10】如下代碼定義了一個類型屬性newvalue,而後進行遍歷訪問該屬性的每個字符,並輸出。代碼以下:

  • import Foundation

  • class NewClass {

  •     class var newvalue:String{                                                                  //定義類型屬性newvalue

  •         return "Hello"

  •     }

  • }

  • print(NewClass.newvalue)

  • print("遍歷NewClass.newvalue")

  • //遍歷類型屬性newvalue的值

  • for index in NewClass.newvalue.characters {

  •     print(index)

  • }

  • 運行結果以下所示:

  • Hello

  • 遍歷NewClass.newvalue

  • H

  • e

  • l

  • l

  • o

在使用類型屬性時須要注意如下2點:

1.let關鍵字不能聲明類型屬性

定義類型屬性時除了有關鍵字class外,還須要使用var關鍵字,但不能使用let關鍵字,不然程序提示錯誤,如如下代碼,此代碼定義了一個類型屬性newvalue。代碼以下:

  • import Foundation

  • class NewClass {

  •     class let newvalue:Int{

  •         return 20

  •     }

  • }

  • print(NewClass.newvalue)

在此代碼中使用了關鍵字let進行了類型屬性的聲明,致使程序出現瞭如下的錯誤:

  • 'let' declarations cannot be computed properties

2.存儲屬性

在類型方法中不能使用存儲屬性,不然程序就會出現錯誤,如如下的代碼,此代碼實現的是輸出字符串"Hello"

  • import Foundation

  • class NewClass {

  •     var count:Int=20

  •     class var newvalue:Int{

  •         return count

  •     }

  • }

  • print(NewClass.newvalue)

其中,count是存儲屬性,newvalue是類型屬性。在代碼中,將str用在newvalue中,致使程序出現瞭如下的錯誤:

  • 'NewClass.Type' does not have a member named 'count'

3.對象不能訪問類型屬性

類型屬性只可使用類去訪問,而不可使用對象進行訪問。不然,就會出現錯誤,如如下的代碼:

  • import Foundation

  • class NewClass {

  •     class var newvalue:Int{

  •         return 20

  •     }

  • }

  • var newClass=NewClass()

  • print(newClass.newvalue)

在此代碼中,定義了一個類型屬性newvalue,但在訪問它時使用了對象,致使程序出現瞭如下錯誤:

  • 'NewClass' does not have a member named 'newvalue'

類型屬性和存儲屬性同樣,除了能夠進行訪問外,還能夠進行修改,其語法形式以下:

  • 類名.類型屬性=修改的內容

【示例8-11】如下程序將類型屬性0變爲200,並輸出。代碼以下所示:

  • import Foundation

  • var value:Int=0

  • class NewClass{

  •     class var count :Int{

  •         get{

  •             let newvalue=value

  •             return newvalue

  •         }

  •         set{

  •             value=newValue

  •         }

  •     }

  • }

  • print("修改前:\(NewClass.count)")

  • NewClass.count=200

  • print("修改後:\(NewClass.count)")

運行結果以下所示:

  • 修改前:0

  • 修改後:200

Swift2.0語言中的屬性監視器

屬性監視器用來監控和響應屬性值的變化。每次屬性被設置值的時候,都會調用屬性監視器,哪怕是新的值和原先的值相同。一個屬性監視器由willSetdidSet組成,其定義形式以下:

  • var 屬性名:數據類型=初始值{

  •          willSet(參數名){

  •                  

  • }

  •          didSet(參數名){

  •                  

  •     }

  • }

其中,willSet在設置新的值以前被調用,它會將新的屬性值做爲固定參數傳入。didSet在新的值被設置以後被調用,會將舊的屬性值做爲參數傳入,能夠爲該參數命名或者使用默認參數名oldValue

【示例8-12】如下將使用屬性監視器監視totalSteps屬性值的變化。代碼以下:

  • import Foundation

  • class StepCounter {

  • var totalSteps: Int = 0 {

  •     //完整的屬性監視器

  •         willSet(newTotalSteps) {

  •             print("新的值爲 \(newTotalSteps)")

  •         }

  •         didSet(old) {

  • if totalSteps > old {                                                                           

  •       print("與原來相比增減了 \(totalSteps - old) 個值")

  •             }

  •         }

  •     }

  • }

  • let stepCounter = StepCounter()

  • stepCounter.totalSteps = 0

  • stepCounter.totalSteps = 200

  • stepCounter.totalSteps = 400

  • stepCounter.totalSteps = 800

運行結果以下所示:

  • 新的值爲 0

  • 新的值爲 200

  • 與原來相比增減了 200 個值

  • 新的值爲 400

  • 與原來相比增減了 200 個值

  • 新的值爲 800

  • 與原來相比增減了 400 個值

注意:在使用屬性監視器時,須要使用注意如下4點:

1.不指定參數名

willSet後面是能夠不指定參數的,這時Swift會使用默認newValue表示新值。例如如下的代碼在沒有指定willSet參數的狀況下,直接使用newValue來輸出新的值。代碼以下:

  • import Foundation

  • class StepCounter {

  •     var totalSteps: Int=0  {

  •         willSet {

  •             print("新的值爲 \(newValue)")

  •         }

  •         didSet (old){

  •             if totalSteps > old  {

  •                 print("與原來相比增減了 \(totalSteps - old) 個值")

  •             }

  •         }

  •     }

  • }

  • let stepCounter = StepCounter()

  • stepCounter.totalSteps = 0

  • stepCounter.totalSteps = 200

運行結果以下所示:

  • 新的值爲 0

  • 新的值爲 200

  • 與原來相比增減了 200 個值

一樣在didSet後面也能夠不指定參數名,此時Swift會使用默認參數名oldValue。如如下的代碼,此是示例8-12的代碼作了一個修改,代碼以下:

  • import Foundation

  • class StepCounter {

  • var totalSteps: Int = 0 {

  •     //完整的屬性監視器

  •         willSet(newTotalSteps) {

  •             print("新的值爲 \(newTotalSteps)")

  •         }

  •         didSet {

  •             if totalSteps > oldValue  {

  •                 print("與原來相比增減了 \(totalSteps - oldValue) 個值")

  •             }

  •         }

  •     }

  • }

  • let stepCounter = StepCounter()

  • stepCounter.totalSteps = 0

2.默認參數不能夠交換使用

在使用willSetdidSet時,它們默認的參數能夠是不能夠交換使用的。例如在willSet中使用的newValue不可使用在didSet中,在didSet中使用的oldValue不可使用在willSet中,不然程序就會出現錯誤。例如如下的代碼,將示例8-12作了一些修改,代碼以下:

  • import Foundation

  • class StepCounter {

  • var totalSteps: Int = 0 {

  •     //完整的屬性監視器

  •         willSet {

  •             print("新的值爲 \(newValue)")

  •         }

  •         didSet {

  • if newValue > oldValue  {                                                                          

  •     print("與原來相比增減了 \(newValue - oldValue) 個值")   //輸出新值和舊值之間的差值

  •             }

  •         }

  •     }

  • }

  • let stepCounter = StepCounter()

在此代碼中,因爲在didSet中使用了willSet中的默認參數,致使程序出現瞭如下的錯誤:

  • Use of unresolved identifier 'newValue'

3.延遲屬性不能使用屬性監視器

在延遲屬性中不可使用屬性監視器,不然程序會出現錯誤。如如下的代碼:

  • class StepCounter {

  •    lazy var totalSteps: Int=0  {

  •         willSet {

  •             print("新的值爲 \(newValue)")

  •         }

  •         didSet {

  •             if totalSteps > oldValue  {

  •                 print("與原來相比增減了 \(totalSteps - oldValue) 個值")

  •             }

  •         }

  •     }

  • }

此代碼中延遲屬性中添加了屬性監視器,致使程序出現了以下的錯誤:

  • lazy properties may not have observers

4.分開使用willSetdidSet

一個完整的屬性監視器由willSetdidSet組成,可是willSetdidSet也能夠單獨使用。例如如下的代碼就只使用了willSet輸出了新值的信息。代碼以下:

  • import Foundation

  • class StepCounter {

  •    var totalSteps: Int=0  {

  •         willSet {

  •             print("新的值爲 \(newValue)")

  •         }

  •     }

  • }

  • let stepCounter = StepCounter()

  • stepCounter.totalSteps = 0

  • stepCounter.totalSteps = 200

  • stepCounter.totalSteps = 600

  • stepCounter.totalSteps = 1200

這裏屬性監視器total只使用了willset,而沒有使用didset。運做結果以下所示:

  • 新的值爲 0

  • 新的值爲 200

  • 新的值爲 600

  • 新的值爲 1200

本文選自:Swift2.0語言快速入門v3.0 大學霸內部資料,轉載請註明出處,尊重技術尊重IT人!

相關文章
相關標籤/搜索