一、以泛型為參數的函數
泛型是Swift語言強大的核心,泛型是對類型的抽象,使用泛型開發者可以更加靈活方便的表達代碼意圖。我們知道,有參函數的參數必須有一個明確的參數類型,有些時候開發者會遇到這樣一種情況,編寫一個函數用于交換兩個變量的值,由于變量有類型之分,實現相同的功能,可能需要重載成多個函數來實現,這大大浪費了開發成本,使用泛型,可以完美的解決這個問題,示例代碼如下:
func exchange<T>(inout param1:T,inout param2:T){ let tmp = param1 param1 = param2 param2 = tmp}var p1 = "15"var p2 = "40"exchange(&p1, param2: &p2)
上面的方法可以實現對任意相同類型變量的交換,函數參數中使用泛型,需要在函數名后的<>中定義參數占位符,如有多個參數占位符,用逗號隔開即可。
二、泛型在類型中的應用
泛型除了可以作為函數的參數、返回值外,在定義類型時,靈活應用泛型也可以解決很多十分棘手的問題,例如實現一個棧結構的集合類型,示例代碼如下:
struct Stack<ItemType> { var items:[ItemType] = [] mutating func push(param:ItemType) { self.items.append(param) } mutating func pop()->ItemType{ return self.items.removeLast() }}//整型棧var obj1 = Stack<Int>()obj1.push(1)obj1.pop()//字符串棧var obj2 = Stack<String>()obj2.push("HS")obj2.pop()
在對使用了泛型的類型進行擴展時,不需要在使用<>進行泛型的定義,直接使用原定義的泛型占位符即可,示例如下:
extension Stack{ func getArray() -> [ItemType] { return items }}
有時候,開發者需要對泛型進行一些約束,例如只允許此泛型是繼承自某個類或者實現了某個協議,示例代碼如下:
class MyClass { }//只有MyClass的子類可以進行Stack棧的創建struct Stack<ItemType:MyClass> { var items:[ItemType] = [] mutating func push(param:ItemType) { self.items.append(param) } mutating func pop()->ItemType{ return self.items.removeLast() }}
在協議中,可以使用另一種方式來進行泛型編程,使用associatedtype關鍵字可以進行類型關聯,示例如下:
protocol MyProtocol { //實現協議時才指定類型 associatedtype ItemType var param:ItemType {get set}}class MyClass:MyProtocol { //由于Swift可以自動識別類型 這是MyProtocol中的ItemType為Int var param: Int = 0}
三、泛型與where子句的結合使用
使用where子句可以對泛型進行更加嚴格約束,使其符合開發者需要的邏輯,示例如下:
//T和C都要遵守整型協議class MyClassTwo<T,C where T:IntegerType,C:IntegerType> { var param1:T var param2:C init(param1:T,param2:C){ self.param1=param1 self.param2=param2 }}var obj3 = MyClassTwo(param1: 1, param2: 1)
新聞熱點
疑難解答