jun 27th, 2014 | comments
swift的屬性與objective-c中的屬性是一樣的,不同的是swift細化了屬性的型別,另外除了類之外,結構體和列舉也可以有屬性。
swift中有這麼幾種屬性:
儲存屬性(stored properties):儲存例項的常量和變數,與類、結構體、列舉的例項相關
計算屬性(computed properties):通過某種方式計算出來的屬性,只與類、結構體的例項相關,列舉沒有計算屬性
型別屬性(type properties):與型別自身相關。
另外,我們可以定義屬性觀察者來監聽屬性值的改變,以執行一些額外的操作。屬性觀察者可以新增到自定義的儲存屬性上,也可以新增到父類繼承而來的屬性上。
下面我們將詳細介紹這些屬性
儲存屬性是最簡單的屬性,它作為類或結構體例項的一部分,用於儲存常量和變數。
關於儲存屬性,有以下幾點:
我們可以給儲存屬性提供乙個預設值,也可以在初始化方法中對其進行初始化,即使是常量型屬性,也可以這樣做。
如果建立乙個常量結構體例項,我們不能修改該例項的變數型儲存屬性。這是因為結構體是值型別,當乙個值型別的例項標記為常量時,它的所有屬性也是常量。由於類是引用型別,所以該條不適用於類型別。
如果我們希望屬性在使用到的時候再初始化,則可以使用懶惰儲存屬性(lazy stored property,使用修飾符@lazy)。懶惰儲存屬性總是應該定義為變數,因為常量型屬性總需要在初始化方法完成之前初始化。
與objective-c不同的是,swift中的屬性不需要乙個與之對應的成員變數,我們不能直接訪問屬性的後備儲存(backing store)。這種方式避免了混淆不同上下文環境下對值的訪問,並將屬性簡化為單
一、明確的宣告。
**清單1:
struct fixedlengthrange
var item1 = fixedlengthrange(firstvalue: 10, length: 10)
let item2 = fixedlengthrange(firstvalue: 10, length: 10)
= 6 // 錯誤:不能修改常量結構體例項的儲存屬性
計算屬性並不儲存實際的值,而是提供乙個getter和乙個可選的setter來間接獲取和設定其它屬性。
關於計算屬性,有以下幾點:
如果計算屬性的setter沒有定義乙個新值的變數名,則預設為newvalue
如果只提供getter,而不提供setter,則該計算屬性為唯讀屬性
我們只能宣告變數型唯讀屬性,因為它們的值不是固定的
如果計算屬性是唯讀的,則可以不使用get{}
計算屬性的實例如**清單2:
**清單2:
struct point
struct size
struct rect
set(newcenter)
}var maxx:float
return float(origin.x) + float(size.width)
}}var square = rect(origin:point(x: 0.0, y: 0.0), size:size(width:100, height:100))
let initialsquarecenter = square.center
square.center = point(x: 15.0, y:15.0)
square.maxx
型別屬性是與型別相關聯的,而不是與型別的例項相關聯。對於某一型別的所有例項,型別屬性都只有乙份拷貝。對於值型別,我們可以定義儲存型別屬性和計算型別屬性。對於類,我們只能定義計算型別屬性。和例項屬性不同的是,我們總是需要給儲存型別屬性乙個預設值。這是因為型別沒有初始化方法來初始化型別屬性。
型別屬性的訪問和設定與例項屬性一樣,不一樣的是,型別屬性通過型別來獲取和設定,而不是型別的例項
**清單3
struct audiochannel
if currentlevel > audiochannel.maxinputlevelforallchannels }}
}var leftchannel = audiochannel()
var rightchannel = audiochannel()
leftchannel.currentlevel = 7
println(leftchannel.currentlevel) // 7
println(audiochannel.maxinputlevelforallchannels) // 7
rightchannel.currentlevel = 11
println(rightchannel.currentlevel) // 10
println(audiochannel.maxinputlevelforallchannels) // 10
屬性觀察者用於監聽和響應屬性值的變化。在每次設定屬性值的時候都會呼叫屬性觀察者方法,即使新舊值是一樣的。我們可以為任何儲存屬性定義屬性觀察者,除了懶惰儲存屬性。我們同樣可以在子類中給繼承而來的屬性新增觀察者。
對於計算屬性,我們不需要定義屬性觀察者,因為我們可以在計算屬性的setter中直接觀察並響應這種值的變化。
我們通過設定以下觀察方法來定義觀察者
willset:在屬性值被儲存之前設定。此時新屬性值作為乙個常量引數被傳入。該引數名預設為newvalue,我們可以自己定義該引數名
didset:在新屬性值被儲存後立即呼叫。與willset相同,此時傳入的是屬性的舊值,預設引數名為oldvalue。
willset與didset只有在屬性第一次被設定時才會呼叫,在初始化時,不會去呼叫這些監聽方法。
Swift中屬性(Property)的分類
在swift的學習過程中,我發現理解屬性,對後續學習類 class 列舉 enumeration 和協議 protocol 很有幫助,現在總結一下swift中屬性的分類,主要分為四大類 儲存例項屬性 stored instance property 儲存在例項的記憶體中的屬性,只有乙份 計算例項屬性...
Swift靜態屬性
在介紹靜態屬性之前,我們先來看乙個類的設計,有乙個account 銀行賬戶 類,假設它有3個屬性 amount 賬戶金額 interestrate 利率 和owner 賬戶名 在這3個屬性中,amount和owner會因人而異,不同的賬戶這些內容是不同的,而所有賬戶的interestrate都是相同...
Swift型別屬性
在 c 或 objective c 中,與某個型別關聯的靜態常量和靜態變數,是作為全域性 global 靜態變數定義的。但是在 swift 中,型別屬性是作為型別定義的一部分寫在型別最外層的花括號內,因此它的作用範圍也就在型別支援的範圍內。使用關鍵字 static 來定義型別屬性。在為類定義計算型型...