Generik Swift
Swift menyediakan generik yang membolehkan anda menulis fungsi dan jenis yang fleksibel dan boleh digunakan semula.
Pustaka standard Swift dibina dengan kod generik.
Jenis tatasusunan dan kamus Swift ialah kedua-dua set generik.
Anda boleh mencipta tatasusunan Int, tatasusunan Rentetan atau mana-mana tatasusunan data jenis Swift yang lain.
Contoh berikut ialah pertukaran fungsi bukan generik yang digunakan untuk menukar dua nilai Int:
// 定义一个交换两个变量的函数 func exchange(inout a: Int, inout b: Int) { let temp = a a = b b = temp } var numb1 = 100 var numb2 = 200 print("交换前数据: \(numb1) 和 \(numb2)") exchange(&numb1, b: &numb2) print("交换后数据: \(numb1) 和 \(numb2)")
Hasil keluaran pelaksanaan program di atas ialah:
交换前数据: 100 和 200 交换后数据: 200 和 100
Generik fungsi boleh mengakses mana-mana Jenis, seperti Int atau String.
Contoh berikut ialah pertukaran fungsi generik yang digunakan untuk menukar dua nilai Int dan String:
func exchange<T>(inout a: T, inout b: T) { let temp = a a = b b = temp } var numb1 = 100 var numb2 = 200 print("交换前数据: \(numb1) 和 \(numb2)") exchange(&numb1, b: &numb2) print("交换后数据: \(numb1) 和 \(numb2)") var str1 = "A" var str2 = "B" print("交换前数据: \(str1) 和 \(str2)") exchange(&str1, b: &str2) print("交换后数据: \(str1) 和 \(str2)")
Hasil keluaran pelaksanaan program di atas ialah:
交换前数据: 100 和 200 交换后数据: 200 和 100 交换前数据: A 和 B 交换后数据: B 和 A
The jenis generik fungsi ini Versi menggunakan nama jenis pemegang tempat (biasanya diwakili oleh huruf T dalam kes ini) dan bukannya nama jenis sebenar (seperti Int, String atau Double). Nama jenis pemegang tempat tidak menunjukkan jenis T mesti, tetapi ia menunjukkan bahawa a dan b mestilah jenis T yang sama, tanpa mengira jenis T yang mewakili. Hanya jenis sebenar yang diluluskan setiap kali fungsi exchange(_:_:) dipanggil boleh menentukan jenis T mewakili.
Satu lagi perbezaan ialah nama jenis pemegang tempat (T) mengikut nama fungsi generik disertakan dalam kurungan sudut (
Jenis generik
Swift membolehkan anda menentukan jenis generik anda sendiri.
Kelas, struktur dan penghitungan tersuai berfungsi dengan mana-mana jenis, sama seperti penggunaan Array dan Kamus
Program di atas ialah:struct TOS<T> { var items = [T]() mutating func push(item: T) { items.append(item) } mutating func pop() -> T { return items.removeLast() } } var tos = TOS<String>() tos.push("Swift") print(tos.items) tos.push("泛型") print(tos.items) tos.push("类型参数") print(tos.items) tos.push("类型参数名") print(tos.items) let deletetos = tos.pop()
Jenis generik lanjutanApabila anda melanjutkan jenis generik (menggunakan kata kunci sambungan), anda tidak perlu memasukkannya dalam definisi sambungan Menyediakan senarai parameter jenis Malah lebih mudah, senarai parameter jenis diisytiharkan dalam definisi jenis asal tersedia dalam sambungan, dan nama parameter daripada jenis asal digunakan sebagai rujukan kepada parameter jenis dalam definisi asal >
Contoh
Contoh berikut melanjutkan jenis TOS generik dan menambah. sifat pengiraan baca sahaja yang dinamakan dahulu, yang akan mengembalikan elemen di bahagian atas tindanan semasa tanpa mengalihkannya daripada tindanan Kecuali["Swift"] ["Swift", "泛型"] ["Swift", "泛型", "类型参数"] ["Swift", "泛型", "类型参数", "类型参数名"]
Hasil keluaran program di atas. pelaksanaan ialah:
struct TOS<T> { var items = [T]() mutating func push(item: T) { items.append(item) } mutating func pop() -> T { return items.removeLast() } } var tos = TOS<String>() tos.push("Swift") print(tos.items) tos.push("泛型") print(tos.items) tos.push("类型参数") print(tos.items) tos.push("类型参数名") print(tos.items) // 扩展泛型 TOS 类型 extension TOS { var first: T? { return items.isEmpty ? nil : items[items.count - 1] } } if let first = tos.first { print("栈顶部项:\(first)") }Kekangan jenis
Kekangan jenis menentukan kelas yang mesti diwarisi daripada kelas yang ditentukan
Sintaks kekangan jenis
<🎜. > Anda boleh menulis kekangan jenis selepas nama parameter jenis, dipisahkan oleh titik bertindih, sebagai jenis Bahagian rantaian parameter Sintaks asas untuk kekangan jenis ini pada fungsi generik adalah seperti berikut (sama seperti sintaks untuk jenis generik. ):["Swift"]
["Swift", "泛型"]
["Swift", "泛型", "类型参数"]
["Swift", "泛型", "类型参数", "类型参数名"]
栈顶部项:类型参数名
Contohfunc someFunction<T: SomeClass, U: SomeProtocol>(someT: T, someU: U) { // 这里是函数主体 }Output pelaksanaan program di atas Hasilnya ialah:
// 函数可以作用于查找一字符串数组中的某个字符串
func findStringIndex(array: [String], _ valueToFind: String) -> Int? {
for (index, value) in array.enumerate() {
if value == valueToFind {
return index
}
}
return nil
}
let strings = ["cat", "dog", "llama", "parakeet", "terrapin"]
if let foundIndex = findStringIndex(strings, "llama") {
print("llama 的下标索引值为 \(foundIndex)")
}
Contoh jenis yang berkaitan
Kata kunci typealias digunakan dalam Swift untuk menetapkan jenis yang berkaitan Apabila mentakrifkan protokol, kadangkala a atau diisytiharkan adalah sangat berguna untuk mempunyai berbilang jenis yang berkaitan sebagai sebahagian daripada definisi protokol daripada pelaksanaan program di atas ialah:
llama 的下标索引值为 2
Di mana kekangan jenis pernyataan
boleh memastikan bahawa jenis mematuhi kekangan yang menentukan bagi fungsi atau kelas generik
.Anda boleh menentukan kekangan parameter melalui mana pernyataan dalam senarai parameter.
Anda boleh menulis pernyataan where serta-merta mengikuti senarai parameter jenis, diikuti dengan satu atau lebih kekangan pada jenis yang berkaitan dan/atau satu atau lebih kekangan antara jenis dan jenis yang berkaitan.
Contoh
Contoh berikut mentakrifkan fungsi generik bernama allItemsMatch untuk menyemak sama ada dua tika Container mengandungi elemen yang sama dalam susunan yang sama.
Jika semua elemen boleh dipadankan, maka kembalikan nilai Boolean yang benar, jika tidak, ia akan menjadi palsu.
protocol Container { // 定义了一个ItemType关联类型 typealias ItemType mutating func append(item: ItemType) var count: Int { get } subscript(i: Int) -> ItemType { get } } // 遵循Container协议的泛型TOS类型 struct TOS<T>: Container { // original Stack<T> implementation var items = [T]() mutating func push(item: T) { items.append(item) } mutating func pop() -> T { return items.removeLast() } // conformance to the Container protocol mutating func append(item: T) { self.push(item) } var count: Int { return items.count } subscript(i: Int) -> T { return items[i] } } var tos = TOS<String>() tos.push("Swift") print(tos.items) tos.push("泛型") print(tos.items) tos.push("参数类型") print(tos.items) tos.push("类型参数名") print(tos.items)
Hasil keluaran pelaksanaan program di atas ialah:
["Swift"] ["Swift", "泛型"] ["Swift", "泛型", "参数类型"] ["Swift", "泛型", "参数类型", "类型参数名"]