
在介紹枚舉之前我們先了解一下Swift中 關(guān)于面向?qū)ο蟮念愋?/strong>
Swift中不僅提供了
面向過程的編程支持,也提供了全面的面向?qū)ο?/code>的支持,與普通的面向?qū)ο蟮木幊陶Z言(只支持類)不同,Swift可以定義枚舉,結(jié)構(gòu)體,類 3種面向?qū)ο蟮念愋停ɑ騭wift類型)、這三種類型,都可以被認為是一種該自定義的數(shù)據(jù)類型,可以被枚舉,結(jié)構(gòu)體,類來定義變量,其中枚舉和結(jié)構(gòu)體是值類型,使用類定義的變量則是引用類型
實例和對象的關(guān)系
在Swift中,實例和對象是不同的, 只有類的實例 才能成為對象,而結(jié)構(gòu)體和枚舉的實例則只能稱為 實例,不能成為對象
在這三種程序單元的內(nèi)部,分別可以定義屬性(存儲屬性,計算屬性)、方法、構(gòu)造器、下標、嵌套類型(包括嵌套類、嵌套結(jié)構(gòu)體、嵌套枚舉)5中類型成員
現(xiàn)在進入正題
1、枚舉的定義和特點
Swift中枚舉:是一種重新定義的類型:和所有的語言的功能類似
作用:主要用于管理一組有限的值的集合
特點:
1.具有面向?qū)ο蟮奶卣?br> 2.支持計算屬性
3.支持實例方法和類型方法
4.允許枚舉遵守指定協(xié)議來提供標準的功能
格式:
enum 枚舉名 {
//使用case關(guān)鍵字列出所有的枚舉值
//枚舉的其他成員
}
//枚舉的定義
enum Season{
case Spring
case Summer
case Fall
case Winter
}
- 上面枚舉中定義了4個枚舉值,每個枚舉值使用一個case定義
- 我們也可以使用一個case 定義多個枚舉值
enum Weekly {
//使用一個case列出多個枚舉值
case Monday,Tuesday,Wednesday,Thursday,Firday,Saturday,Sunday
}
2、枚舉的使用
與C、OC的枚舉不同,Swift的枚舉成員不會被分配一個默認的整數(shù)值,
【重點】也就是說,Swift的枚舉名本身就代表一個枚舉實例,對應(yīng)一個枚舉值,與整數(shù)值沒有任何關(guān)系,
定義了Swift的任意類型之后,大致可從如下幾個方面來使用該類型
1->聲明變量
2->創(chuàng)建實例
3->訪問類型屬性
4->調(diào)用類型方法
5->派生子類。但Swift中 只有類才支持繼承,枚舉和結(jié)構(gòu)體都不支持繼承,因此枚舉和結(jié)構(gòu)體都不能派生子類
【注意】:這5中功能,是面向?qū)ο蟮目偩V,以后無論學(xué)習(xí)任何面向?qū)ο蟮木幊陶Z言的時候,有了類之后,大致上都是使用上面列出的5種功能
//1->聲明
var day:Weekly
//2->創(chuàng)建實例
//使用已有的枚舉實例賦值(因為枚舉名本身就代表一個枚舉實例,所以不需要創(chuàng)建實例)
day = Weekly.Firday
print(day)
- 在定義day的時候已經(jīng)知道了day的類型 所以在后面使用的時候 可以省略 前面的類型
day = .Firday
3、枚舉和Switch語句
【注】因為Switch語言中,Switch語句 必須是
完備的,也就是說Switch語句的case必須覆蓋所有可能的情況,否則最后必須添加default語句
let chooseDay = Weekly.Monday
switch chooseDay {
case .Monday :
print("1")
case .Tuesday:
print("2")
case .Wednesday:
print("3")
case .Thursday :
print("4")
case .Firday:
print("5")
case .Saturday:
print("6")
case .Sunday:
print("7")
}
因為上面程序中的case已經(jīng)覆蓋了 所有枚舉值,所以switch語句可以省略,default 分支,當然也可以添加上:只是會報個警告
Default will never be executed
哦,對了 如果 你運行的時候,在switch chooseDay { 這行報警告Switch condition evaluates to a constant的話,可以把要聲明的變量放到函數(shù)外
3、原始值
有點類似于,C、OC的枚舉,通過原始值可以為每個枚舉實例指定一個簡單類型,如Int Double String等
語法:enum 枚舉名 : 原始值類型 {
case 枚舉值 = 原始值
}
- 【注】 Swift并不要對每個枚舉值都指定,原始值。
Swift可以根據(jù)已指定的原始值,推斷出它前后的所有枚舉值
- 原始值為:Int 類型
enum weekDay2 :Int {
case Monday=1,Tuesday,Wednesday=5,Thursday,Firday,Saturday,Sunday
}
//可以推斷,Tuesday的原始值為2 Thursday=6 Firday=7
原始值為:String類型
Swift也可以為 枚舉值分配隱式的原始值--隱式的原始值與變量名同名
這里程序只為Left 顯式分配了原始值,意味著只有l(wèi)eft的原始值是“Left” 其余的原始值 都是隱式原始值,也就是“Up”,"Down","Right"
【注】枚舉要么完全不指定原始值,要么所有枚舉都具有原始值,為了讓所有的枚舉都有原始值,即可讓系統(tǒng)自動推斷,也可指定顯示指定
enum Orientation :String {
case Up ,Down,Left="左",Right
}
現(xiàn)在已經(jīng)有了 原始值 ,接下來即可使用枚舉提供的如下的構(gòu)造器和屬性
init?(rawValue:):可能失敗的構(gòu)造器:根據(jù)原始值返回對應(yīng)的枚舉值
hashValue:根據(jù)枚舉值 獲得原始值
let Orient = Orientation.Up
print("\\(Orient.hashValue)")//通過枚舉值-->原始值
//輸出Up
let MyOrient = Orientation(rawValue:"左") //原始值 --> 枚舉值
//因為init?(rawValue:)是一個 可能失敗的構(gòu)造器 所以要執(zhí)行可選綁定
if let newOrient = MyOrient {
print(newOrient)
}
//輸出 Left
print("\\(Orient.hashValue)")//Orient.hashValue 獲取哈希值
//輸出 0
4、 關(guān)聯(lián)值
枚舉除了可以定義一組,枚舉成員之外,還可以為枚舉成員定義一組關(guān)聯(lián)值,--Swift并不要求各枚舉 具有相同的關(guān)聯(lián)值,關(guān)聯(lián)值就是枚舉實例攜帶的一些額外的數(shù)據(jù),有點類似于枚舉值的屬性。
語法: 語法:case 枚舉值(元組語法)
enum Planet {
case Mercury (weight:Double ,density:Double,name:String)
case Venus (Double ,Double)
case Jupiter
}
//Mercury Venus攜帶關(guān)聯(lián)值,而且Mercury的關(guān)聯(lián)值還指定了名稱,雖然指定了名稱但是,程序依然無法向訪問元組成員一樣訪問關(guān)聯(lián)值
var p1 = Planet.Mercury(weight: 10, density: 10, name: "lpx")
- 【注】:當程序為枚舉值 指定了 關(guān)聯(lián)值之后,程序使用這些枚舉值的時,必須指定它的關(guān)聯(lián)值。
** 關(guān)聯(lián)值的訪問**
- 枚舉中的關(guān)聯(lián)值:需要聲明額外的變量(常量),并將枚舉的關(guān)聯(lián)值綁定到這些變量或常量
//【注】如果程序打算將某個枚舉值的所有關(guān)聯(lián)值都提取為變量或常量,也可只將一個var、let 放置在枚舉成員的前面。
//eg: case let .Mercury(weight, density, last ):
switch p1 {
//這里就相當于 元組值的綁定
case Planet.Mercury(let weight , let density,let name ):
print("weight= \\(weight) density=\\(density) name=\\(last)")
default :
print("")
}
//輸出 weight= 10.0 density=10.0 name=lpx
5、枚舉的函數(shù)用法(【用的比較少】【而且沒有提示】)
對于有關(guān)聯(lián)值的枚舉,甚至可以被當做函數(shù)使用,該函數(shù)總是可以根據(jù)關(guān)聯(lián)值創(chuàng)建對應(yīng)的枚舉實例,與普通函數(shù)類似的是,可作為函數(shù)使用的枚舉,也可以被賦值給函數(shù)類型的變量,
let fn = Planet.Venus//將Planet.Venus賦給fn變量 得知fn是一個類型為(Double,Double)->Planet的函數(shù)
let g1 = fn(10,10)//返回的就是關(guān)聯(lián)值為 10,10的Venus的枚舉值與直接獲取的Planet.Venus(10, 10)的結(jié)果相同
print(g1)
let g2 = Planet.Venus(10, 10)
print(g2)//這兩個輸出的一樣的 Venus(10.0, 10.0)
6、遞歸枚舉
在有些情況下,枚舉值所包含的關(guān)聯(lián)值類型 又是該枚舉本身,此時就形成了遞歸枚舉,
enum Weekly2 {
indirect case Monday (next:Weekly2)
case Tuesday (String)
case Wednesday
case Thursday
case Firday
indirect case Saturday(next:Weekly2)
case Sunday
}
- Swift也支持用 indirect 修飾枚舉本身,把indirect放到enum前面,這就相當于 在每個枚舉值的case前都是用了indirect