Swift class和struct異同點(diǎn)

相同點(diǎn):

1.定義屬性用于存儲(chǔ)值 (property)
2.定義方法用于提供功能 (function)
3.定義下標(biāo)操作使得可以通過(guò)下標(biāo)語(yǔ)法來(lái)訪(fǎng)問(wèn)實(shí)例所包含的值 (subscript)
4.定義構(gòu)造器用于生成初始化值 (initializers)
5.通過(guò)擴(kuò)展以增加默認(rèn)實(shí)現(xiàn)的功能 (extension)
6.實(shí)現(xiàn)協(xié)議以提供某種標(biāo)準(zhǔn)功能 (protocol)

不同點(diǎn):

1.class是引用類(lèi)型;struct是值類(lèi)型
2.class支持繼承;struct不支持繼承
3.class聲明的方法修改屬性時(shí)不需要mutating關(guān)鍵字俊柔;struct需要
4.class中每一個(gè)成員變量都必須被初始化框往,否則編譯器會(huì)報(bào)錯(cuò)匙赞,而struct不需要屡穗,編譯器會(huì)自動(dòng)幫我們生成init函數(shù),給變量賦一個(gè)默認(rèn)值
5.class支持引用計(jì)數(shù)(reference counting)(允許對(duì)一個(gè)類(lèi)的多次引用)番枚,struct不支持
6.class支持type casting(類(lèi)型轉(zhuǎn)換)(允許在運(yùn)行時(shí)檢查和解釋一個(gè)類(lèi)實(shí)例的類(lèi)型)法严,struct不支持
7.class支持deinitializers(析構(gòu)器)(允許一個(gè)類(lèi)實(shí)例釋放任何其所被分配的資源),struct不支持
8.變量賦值方式不同(深淺copy)葫笼,class淺拷貝深啤,struct深拷貝,class的賦值是傳遞引用渔欢,struct則是copy傳值,不是使用引用計(jì)數(shù)墓塌。
9.內(nèi)存管理:struct存儲(chǔ)在stack中,class存儲(chǔ)在heap中奥额、
10.方法派發(fā)方式:struct的方法調(diào)用是靜態(tài)綁定苫幢,而class的方法調(diào)用是動(dòng)態(tài)實(shí)現(xiàn)

Tip: class的對(duì)象是引用類(lèi)型,而struct是值類(lèi)型垫挨。所以class的賦值是傳遞引用韩肝,則是copy傳值,不是使用引用計(jì)數(shù)。
class為了支持的額外功能則會(huì)增加其復(fù)雜性九榔。一般,更傾向使用選擇struct和enum,因?yàn)樗麄兏菀桌斫?而class哀峻,則在合適和必要的時(shí)候使用。實(shí)際上哲泊,這意味著大多數(shù)的自定義數(shù)據(jù)類(lèi)型定義為struct和enum就可以了剩蟀。

class和struct的選擇
struct實(shí)例總是通過(guò)值傳遞,class實(shí)例總是通過(guò)引用傳遞切威。這意味兩者適用不同的任務(wù)育特。當(dāng)你在考慮一個(gè)工程項(xiàng)目的數(shù)據(jù)結(jié)構(gòu)和功能的時(shí)候,你需要決定每個(gè)數(shù)據(jù)結(jié)構(gòu)是定義成struct還是class先朦。
按照通用的準(zhǔn)則缰冤,當(dāng)符合一條或多條以下條件時(shí),請(qǐng)考慮構(gòu)建struct

  • 該數(shù)據(jù)結(jié)構(gòu)的主要目的是用來(lái)封裝少量相關(guān)簡(jiǎn)單數(shù)據(jù)值喳魏。
  • 有理由預(yù)計(jì)該數(shù)據(jù)結(jié)構(gòu)的實(shí)例在被賦值或傳遞時(shí)棉浸,封裝的數(shù)據(jù)將會(huì)被拷貝而不是被引用。
  • 該數(shù)據(jù)結(jié)構(gòu)中儲(chǔ)存的值類(lèi)型屬性刺彩,也應(yīng)該被拷貝迷郑,而不是被引用枝恋。
  • 該數(shù)據(jù)結(jié)構(gòu)不需要去繼承另一個(gè)既有類(lèi)型的屬性或者行為。
  • 使用struct和protocol來(lái)實(shí)現(xiàn)model繼承和共享行為嗡害,如下代碼所示:
protocol AnimalCommonProtocol {
    var name: String? { get set }
    var weight: Double { get set }
    func run()
}

struct Cat : AnimalCommonProtocol {
    func run() {
        print("cat run")
    }
    var name: String?
    var weight: Double
    var gender: String?
}

struct Dog : AnimalCommonProtocol {
    func run() {
        print("dog run")
    }
    
    var name: String?
    var weight: Double
    var type: String?
}

總結(jié)起來(lái)就是一句話(huà):能使用struct就不要使用class
為什么優(yōu)選struct:

  • 使用struct不需要考慮內(nèi)存泄漏和多線(xiàn)程讀寫(xiě)的問(wèn)題鼓择,因?yàn)樵趥鬟f值的時(shí)候它會(huì)進(jìn)行值的copy
  • struct存儲(chǔ)在stack中,class存儲(chǔ)在heap中就漾,struct更快
  • 在運(yùn)行時(shí),struct在性能方面更優(yōu)于class念搬,原因是struct的方法調(diào)用是靜態(tài)綁定抑堡,而class的方法調(diào)用是動(dòng)態(tài)實(shí)現(xiàn)的。這就是盡可能得使用struct代替class的又一個(gè)好的原因朗徊。

恒等運(yùn)算符
因?yàn)閏lass是引用類(lèi)型首妖,有可能有多個(gè)常量和變量在幕后同時(shí)引用同一個(gè)類(lèi)實(shí)例。(對(duì)于struct和enum來(lái)說(shuō)爷恳,這并不成立有缆。因?yàn)樗鼈冏鳛橹殿?lèi)型,在被賦予到常量温亲、變量或者傳遞到函數(shù)時(shí)棚壁,其值總是會(huì)被拷貝。)
如果能夠判定兩個(gè)常量或者變量是否引用同一個(gè)類(lèi)實(shí)例將會(huì)很有幫助栈虚。為了達(dá)到這個(gè)目的袖外,Swift 內(nèi)建了兩個(gè)恒等運(yùn)算符:

  • 等價(jià)于(===)
  • 不等價(jià)于(!==)
    運(yùn)用這兩個(gè)運(yùn)算符檢測(cè)兩個(gè)常量或者變量是否引用同一個(gè)實(shí)例:
if tenEighty === alsoTenEighty {
    print("tenEighty and alsoTenEighty refer to the same Resolution instance.")
}
//打印 "tenEighty and alsoTenEighty refer to the same Resolution instance."

注意,等價(jià)于(用三個(gè)=表示)與等于(用兩個(gè)=表示)不同:
1.等價(jià)于表示兩個(gè)類(lèi)類(lèi)型(class type)的常量或者變量引用同一個(gè)類(lèi)實(shí)例魂务。
2.等于表示兩個(gè)實(shí)例的值相等相同曼验,判定時(shí)要遵照設(shè)計(jì)者定義的評(píng)判標(biāo)準(zhǔn),因此相對(duì)于相等來(lái)說(shuō)粘姜,這是一種更加合適的叫法鬓照。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市孤紧,隨后出現(xiàn)的幾起案子豺裆,更是在濱河造成了極大的恐慌,老刑警劉巖坛芽,帶你破解...
    沈念sama閱讀 217,734評(píng)論 6 505
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件留储,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡咙轩,警方通過(guò)查閱死者的電腦和手機(jī)获讳,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,931評(píng)論 3 394
  • 文/潘曉璐 我一進(jìn)店門(mén),熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)活喊,“玉大人丐膝,你說(shuō)我怎么就攤上這事。” “怎么了帅矗?”我有些...
    開(kāi)封第一講書(shū)人閱讀 164,133評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵偎肃,是天一觀的道長(zhǎng)。 經(jīng)常有香客問(wèn)我浑此,道長(zhǎng)累颂,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,532評(píng)論 1 293
  • 正文 為了忘掉前任凛俱,我火速辦了婚禮紊馏,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘蒲犬。我一直安慰自己朱监,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,585評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布原叮。 她就那樣靜靜地躺著赫编,像睡著了一般。 火紅的嫁衣襯著肌膚如雪奋隶。 梳的紋絲不亂的頭發(fā)上擂送,一...
    開(kāi)封第一講書(shū)人閱讀 51,462評(píng)論 1 302
  • 那天,我揣著相機(jī)與錄音唯欣,去河邊找鬼团甲。 笑死,一個(gè)胖子當(dāng)著我的面吹牛黍聂,可吹牛的內(nèi)容都是我干的躺苦。 我是一名探鬼主播,決...
    沈念sama閱讀 40,262評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼产还,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼匹厘!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起脐区,我...
    開(kāi)封第一講書(shū)人閱讀 39,153評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤愈诚,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后牛隅,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體炕柔,經(jīng)...
    沈念sama閱讀 45,587評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,792評(píng)論 3 336
  • 正文 我和宋清朗相戀三年媒佣,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了匕累。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,919評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡默伍,死狀恐怖欢嘿,靈堂內(nèi)的尸體忽然破棺而出衰琐,到底是詐尸還是另有隱情,我是刑警寧澤炼蹦,帶...
    沈念sama閱讀 35,635評(píng)論 5 345
  • 正文 年R本政府宣布羡宙,位于F島的核電站,受9級(jí)特大地震影響掐隐,放射性物質(zhì)發(fā)生泄漏狗热。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,237評(píng)論 3 329
  • 文/蒙蒙 一虑省、第九天 我趴在偏房一處隱蔽的房頂上張望斗搞。 院中可真熱鬧,春花似錦慷妙、人聲如沸。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,855評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至隙弛,卻和暖如春架馋,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背全闷。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 32,983評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工叉寂, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人总珠。 一個(gè)月前我還...
    沈念sama閱讀 48,048評(píng)論 3 370
  • 正文 我出身青樓屏鳍,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親局服。 傳聞我的和親對(duì)象是個(gè)殘疾皇子钓瞭,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,864評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容