較傳統的OC語言,Swift使用了更多的結構體,在 Swift 中,所有的基本類型,都是結構體類型
- 整數(Integer)
- 浮點數(floating-point)
- 布爾值(Boolean)
- 字符串(string)
- 數組(array)
- 字典(dictionary)
在比較類和結構體之間的區別之前,先了解兩個概念,引用類型和值類型:
引用類型
引用類型在被賦予到一個變量、常量或者被傳遞到一個函數時,其值不會被拷貝。因此,引用的是已存在的實例本身而不是其拷貝
值類型
它們的實例,以及實例中所包含的任何值類型屬性,在代碼中傳遞的時候都會被復制
類和結構體對比
本質區別:
- 類是引用類型,實例是通過引用傳遞
- 結構體是值類型,實例是通過值傳遞
Swift 中類和結構體有很多共同點
- 定義屬性用于存儲值
- 定義方法用于提供功能
- 定義下標操作使得可以通過下標語法來訪問實例所包含的值
- 定義構造器用于生成初始化值
- 通過擴展以增加默認實現的功能
- 實現協議以提供某種標準功能
與結構體相比,類還有如下的附加功能
- 繼承允許一個類繼承另一個類的特征
- 類型轉換允許在運行時檢查和解釋一個類實例的類型
- 析構器允許一個類實例釋放任何其所被分配的資源
- 引用計數允許對一個類的多次引用
結構體和類的定義語法
結構體定義語法
struct SomeStructure {
// 在這里定義結構體
}
所有結構體都有一個自動生成的成員逐一構造器,用于初始化新結構體實例中成員的屬性
類定義語法 (一)
不繼承NSObject的類,叫做基類
class SomeClass {
// 在這里定義類
}
類定義語法 (二)
這種類繼承自NSObject,可以使用OC中的 NSObject 的特性 eg:KVO,runtime
class SomeClass: NSObject {
// 在這里定義類
}
類和結構體使用注意
類是引用類型,其屬性如果是可變類型,可以直接修改,修改后類型不變
結構體是值類型,初始化完成后,一般情況下,不允許修改其屬性;如果修改其屬性,會生成一個新的結構體;如果想不改變結構體的類型,需要定義一個mutating修飾的方法,專門用來修改其屬性
寫時復制 (copy-on-write)
Swift用了大量的結構體,每次修改都是復制一份,是不是很浪費內存?
答:在 Swift 標準庫中,像是 Array,Dictionary 和 Set 這樣的集合類型是通過一種叫做寫時復制 (copy-on-write) 的技術實現的,該技術優化了這一問題,讓結構體在核合適的時候才進行復制。
類和結構體的選擇
當符合一條或多條以下條件時,請考慮構建結構體:
- 該數據結構的主要目的是用來封裝少量相關簡單數據值;
- 有理由預計該數據結構的實例在被賦值或傳遞時,封裝的數據將會被拷貝而不是被引用;
- 該數據結構中儲存的值類型屬性,也應該被拷貝,而不是被引用;
- 該數據結構不需要去繼承另一個既有類型的屬性或者行為。