Swift5.5學(xué)習(xí)筆記八:結(jié)構(gòu)和類(Stuctures And Classes)

//結(jié)構(gòu)和類
//結(jié)構(gòu)和類是通用的、靈活的結(jié)構(gòu),它們成為程序代碼的代碼塊。
//您可以使用與定義常量、變量和函數(shù)相同的語法來定義屬性和方法以向結(jié)構(gòu)和類添加功能。

//一、結(jié)構(gòu)和類的比較
//Swift 中的結(jié)構(gòu)和類有很多共同點。
//相同點:
//定義存儲值的屬性
//定義提供功能的方法
//定義下標(biāo)以使用下表語法訪問它們的值
//定義初始值設(shè)定項以設(shè)置其初始狀態(tài)
//擴展默認實現(xiàn)之外的功能
//提供符合協(xié)議的標(biāo)準(zhǔn)功能

//另外,類還具有一些結(jié)構(gòu)不具備的功能:
//一個類可以繼承另外一個類特性的能力
//類型轉(zhuǎn)換使您能夠在運行時檢查和解釋類的實例的類型
//析構(gòu)器使類的實例能夠釋放它分配的任何資源
//引用計數(shù)允許對一個類實例有多個引用

//1.定義語法
//結(jié)構(gòu)和類具有相似的定義語法。用struct關(guān)鍵字引入結(jié)構(gòu),用關(guān)鍵字class引入類。兩者都將整個定義放在一對大括號中:

struct SomeStructure {
    // structure definition goes here
}
class SomeClass {
    // class definition goes here
}

//備注:每當(dāng)你定義一個新的結(jié)構(gòu)或類時,你就定義了一個新的Swift類型。
//使用大駝峰(UpperCamelCase)命名類型(例如SomeStructure和SomeClass)以匹配標(biāo)準(zhǔn)Swift類型(例如String, Int, 和Bool)的大小寫。
//使用小駝峰(lowerCamelCase)命名屬性和方法(例如frameRate和incrementCount)以將它們與類型名稱區(qū)分開來。

//這是結(jié)構(gòu)定義和類定義的示例:

struct Resolution {
    var width = 0
    var height = 0
}


class VideoMode {
    var resolution = Resolution()
    var interlaced = false
    var frameRate = 0.0
    var name: String?
}

//上面的示例定義了一個名為Resolution的新結(jié)構(gòu),用于描述基于像素的顯示分辨率。
//這個結(jié)構(gòu)有兩個存儲屬性,稱為width和height。存儲屬性是常量或變量作為結(jié)構(gòu)或類的一部分捆綁在一起存儲的。這兩個Int類型屬性的處事之為0。

//上面的示例還定義了一個名為VideoMode的新類,用于描述視頻顯示的特定視頻模式。
//這個類有四個存儲變量屬性。第一個 resolution用一個Resolution結(jié)構(gòu)實例初始化,它推斷屬性類型為Resolution。
//其他三個屬性,VideoMode實例將屬性interlaced設(shè)置false、播放幀速率frameRate設(shè)置為0.0,name是一個可選String值來初始化,name屬性是一個可選類型自動被賦予一個默認值nil。

//2.結(jié)構(gòu)和類實例
//創(chuàng)建實例的語法對于結(jié)構(gòu)和類都非常相似:

let someResolution = Resolution()
let someVideoMode = VideoMode()

//3.訪問屬性
//您可以使用點語法訪問實例的屬性。在點語法中,您在實例名稱后立即寫入屬性名稱,用句點(.)分隔,不帶任何空格:

print("The width of someResolution is \(someResolution.width)")
// Prints "The width of someResolution is 0"

//在本例中,someResolution.width引用someResolution的width屬性,并返回其默認初始值0。

//您可以深入到子屬性,例如VideoMode的resolution屬性的resolution屬性中的width屬性:

print("The width of someVideoMode is \(someVideoMode.resolution.width)")
// Prints "The width of someVideoMode is 0"

//您還可以使用點語法為變量屬性分配新值:

someVideoMode.resolution.width = 1280
print("The width of someVideoMode is now \(someVideoMode.resolution.width)")
// Prints "The width of someVideoMode is now 1280"

//4.結(jié)構(gòu)類型的成員初始化器
//所有結(jié)構(gòu)都有一個聰明的、自動生成的初始化器,您可以使用它來初始化新結(jié)構(gòu)實例的成員屬性。新實例屬性的初始值可以按名稱傳遞給成員初始化器:

let vga = Resolution(width: 640, height: 480)

//與結(jié)構(gòu)不同,類實例不接收默認的成員初始化器

//二、結(jié)構(gòu)和枚舉是值類型
//值類型是一個類型,當(dāng)它被分配給一個變量或常量,或者把它傳遞給一個函數(shù)作為參數(shù)時,它的值是被復(fù)制過去的。
//在前面的章節(jié)中,您實際上已經(jīng)廣泛使用了值類型。
//事實上,Swift中的所有基本類型——整數(shù)、浮點數(shù)、布爾值、字符串、數(shù)組和字典都是值類型,它們是以結(jié)構(gòu)的方式被實現(xiàn)。
//Swift中所有結(jié)構(gòu)和枚舉都是值類型。這意味著你創(chuàng)建的任何結(jié)構(gòu)和枚舉實例,以及它們作為屬性的任何值類型,在你的代碼中傳遞時都會被復(fù)制。

//備注:
//標(biāo)準(zhǔn)庫定義的集合(如數(shù)組、字典和字符串)使用優(yōu)化來降低復(fù)制的性能成本。
//這些集合不是立即復(fù)制,而是在原始實例和任何副本之間共享存儲元素的內(nèi)存。
//如果集合的其中一個副本被修改,則元素將在修改之前復(fù)制。您在代碼中看到的行為好像立即復(fù)制了一副新副本

//下面這個例子,它使用了上一個例子中的Resolution結(jié)構(gòu):

let hd = Resolution(width: 1920, height: 1080)
var cinema = hd

//此示例聲明了一個名為hd的常量,并將其設(shè)置為Resolution實例,初始化為使用全高清視頻的寬度和高度(1920 像素寬 x 1080 像素高)
//然后它聲明一個變量cinema,并將其設(shè)置為hd的當(dāng)前值。
//因為Resolution是一個結(jié)構(gòu),當(dāng)把它分配給cinema的時候,根據(jù)現(xiàn)有實例的復(fù)制了一份副本并分配給cinema。
//雖然hd和cinema現(xiàn)在有相同的寬度和高度,但是它們是兩種完全不同的實例

//接下來,將cinema的width屬性修改為用于數(shù)字電影放映的稍寬的2K標(biāo)準(zhǔn)的寬(2048 像素寬,1080 像素高):

cinema.width = 2048

//檢查cinema的width屬性顯示它確實已更改為2048:

print("cinema is now \(cinema.width) pixels wide")
// Prints "cinema is now 2048 pixels wide"

//但是,原始hd實例的width屬性仍然是舊值1920:

print("hd is still \(hd.width) pixels wide")
// Prints "hd is still 1920 pixels wide"

//當(dāng)cinema被賦予hd的當(dāng)前值時,存儲在hd的值被復(fù)制到新cinema實例中。
//最終結(jié)果是兩個完全獨立的實例包含相同數(shù)值的。但是,由于它們是獨立的實例,因此設(shè)置cinema的值為2048的寬度,不會影響hd中存儲的寬度

//枚舉中的情況同樣是這樣:

enum CompassPoint {
    case north, south, east, west
    mutating func turnNorth() {
        self = .north
    }
}
var currentDirection = CompassPoint.west
let rememberedDirection = currentDirection
currentDirection.turnNorth()

print("The current direction is \(currentDirection)")
print("The remembered direction is \(rememberedDirection)")
// Prints "The current direction is north"
// Prints "The remembered direction is west"

//當(dāng)rememberedDirection被分配為currentDirection的值時,它實際上復(fù)制了一份該值的副本。
//當(dāng)更改currentDirection的值后,不會影響存儲在rememberedDirection的值

//三、類是引用類型
//不同于值類型,當(dāng)引用類型分配給常量或變量,或者傳遞給函數(shù)的是,它不會復(fù)制一份副本,而使用同一個已經(jīng)存在的實例的引用

//這是一個示例,使用上面定義的類VideoMode:

let tenEighty = VideoMode()
tenEighty.resolution = hd
tenEighty.interlaced = true
tenEighty.name = "1080i"
tenEighty.frameRate = 25.0

//接下來,tenEighty分配給一個alsoTenEighty常量,alsoTenEighty修改的幀速率:

let alsoTenEighty = tenEighty
alsoTenEighty.frameRate = 30.0

//由于類是引用類型,tenEighty和alsoTenEighty實際上都指向同一個VideoMode實例。實際上,它們只是同一個實例的兩個不同名稱
//檢查tenEighty的frameRate屬性表明它正確展示為VideoMode實例的新幀速率30.0:

print("The frameRate property of tenEighty is now \(tenEighty.frameRate)")
// Prints "The frameRate property of tenEighty is now 30.0"

//請注意,tenEighty和alsoTenEighty被聲明為常量,而不是變量。但是,仍然可以更改tenEighty.frameRate和alsoTenEighty.frameRate的值
//因為tenEighty和alsoTenEighty作為常量本身的值實際上并沒有改變。
//tenEighty和alsoTenEighty他們自己不“存儲”VideoMode實例——相反,他們都引用VideoMode的實例。
//改變frameRate是改變VideoMode的屬性,而不是改變VideoMode的常量引用的值。

//1.身份運算符
//因為類是引用類型,所以多個常量和變量可能在幕后引用同一個類的單個實例。
//注意:結(jié)構(gòu)和枚舉并非如此,因為它們在分配給常量或變量或傳遞給函數(shù)時總是會被復(fù)制。
//有時,找出兩個常量或變量是否指向一個類的同一個實例會很有用。為了實現(xiàn)這一點,Swift提供了兩個身份運算符:

//等同于(===)
//不等同于(!==)

if tenEighty === alsoTenEighty {
    print("tenEighty and alsoTenEighty refer to the same VideoMode instance.")
}
// Prints "tenEighty and alsoTenEighty refer to the same VideoMode instance."

//請注意,相同于(由三個等號或===表示)并不意味著與等于(由兩個等號或==表示相同。
//相同于意味著兩個常量或變量類型引用的類實例完全相同。等于意味著兩個實例在值上被視為相等或等效。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 本頁包含內(nèi)容: 類和結(jié)構(gòu)體對比結(jié)構(gòu)體和枚舉是值類型類是引用類型類和結(jié)構(gòu)體的選擇字符串、數(shù)組、和字典類型的賦值與復(fù)制...
    雨影閱讀 288評論 0 0
  • 前言類和結(jié)構(gòu)體是人們構(gòu)建代碼所用的一種通用且靈活的構(gòu)造體。我們可以使用完全相同的語法規(guī)則來為類和結(jié)構(gòu)體定義屬性(常...
    Mr_yinwei閱讀 782評論 0 1
  • 翻譯能力有限,如有不對的地方,還請見諒!希望對Swift的學(xué)習(xí)者有所幫助,使用的編寫工具:JQNote InNot...
    JackYan0927閱讀 450評論 0 0
  • 1. 枚舉 枚舉為一組相關(guān)的值定義了一個共同的類型,使你可以在你的代碼中以類型安全的方式來使用這些值。 在 Swi...
    路飛_Luck閱讀 493評論 0 1
  • 類和結(jié)構(gòu) 類和結(jié)構(gòu)是通用的,靈活的構(gòu)造,它們成為程序代碼的構(gòu)建塊。您可以使用與常量,變量和函數(shù)完全相同的語法來定義...
    Fuuqiu閱讀 201評論 0 0

友情鏈接更多精彩內(nèi)容