[英]Swift - find object in array of enums with associated values
我有這個枚舉:
enum Animal {
case cat(CatModel)
case dog(DogModel)
}
還有一系列動物:
var animals: [Animal]
我需要通過 Dog 沒有的屬性在此數組中找到 Cat object。 例如litterBoxId
。
let cat = animals.first(where: {$0.litterBoxId == 7})
這當然有一個錯誤:
Value of type 'MyViewController.Animal' has no member 'litterBoxId'
我怎樣才能做到這一點? 我也試過
($0 as CatModel).litterBoxId
這可能不是對枚舉的良好使用,但它是如何工作的:
struct CatModel {
let litterBoxID: Int
}
struct DogModel {
let litterBoxID: Int
}
enum Animal {
case cat(CatModel)
case dog(DogModel)
var litterBoxId: Int {
switch self {
case .cat(let cat): return cat.litterBoxID
case .dog(let dog): return dog.litterBoxID
}
}
}
var animals: [Animal] = []
let cat = animals.first(where: { $0.litterBoxId == 7 })
使用協議會更好:
struct CatModel: Animal {
let litterBoxID: Int
}
struct DogModel: Animal {
let litterBoxID: Int
}
protocol Animal {
var litterBoxID: Int { get }
}
var animals: [Animal] = []
let cat = animals.first(where: { $0.litterBoxID == 7 })
您可以通過 2 種方式使用模式匹配來完成此操作。
使用開關:
let cat = animals.first(where: {
switch $0 {
case .cat(let catModel) where catModel.litterBoxId == 7:
return true
default:
return false
}
})
或者如果:
let cat = animals.first(where: {
if case .cat(let catModel) = $0, catModel.litterBoxId == 7 {
return true
}
return false
})
更新:正如@Alexander-ReinstateMonica 在他的 commnet 中提到的,將這個邏輯隱藏在 function 后面會更合適,如下所示:
extension Animal {
func matches(litterboxID: Int) -> Bool {
switch self {
case .cat(let catModel) where catModel.litterBoxId == 7:
return true
default:
return false
}
}
}
然后你的代碼會更干凈:
let cat = animals.first(where: { $0.matches(litterboxID: 7) })
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.