如果右侧是引用而不是硬编码类型,我无法弄清楚如何使用is
运算符在Swift中进行类型比较。
例如,
class GmBuilding { }
class GmOffice: GmBuilding { }
class GmFactory: GmBuilding { }
class GmStreet {
var buildings: [GmBuilding] = []
func findAllBuildingsOfType(buildingType: GmBuilding.Type) -> [GmBuilding] {
var result: [GmBuilding] = []
for building in self.buildings {
if building is buildingType { // complains that buildingType is not a type
result.append(building)
}
}
return result
}
}
let myStreet = GmStreet()
var buildingList: [GmBuilding] = myStreet.findAllBuildingsOfType(GmOffice.self)
它抱怨建筑类型不是类型'。如何才能工作?
答案 0 :(得分:3)
通用方法可以做你想做的事:
func findAllBuildingsOfType<T: GmBuilding>(buildingType: T.Type) -> [GmBuilding] {
// you can use `filter` instead of var/for/append
return buildings.filter { $0 is T }
}
只要您确实只想在编译时确定类型,这将有效:
let myStreet = GmStreet()
let buildingList = myStreet.findAllBuildingsOfType(GmOffice.self)
// T is set at compile time to GmOffice --------^
但是,通常在出现此问题时,后续问题是,如何将GmOffice.self
存储在变量中,然后在运行时确定类型?并且 将无法使用此技术。但是如果在编译时静态修复类型对你来说足够了,那就应该这样做。
答案 1 :(得分:2)
如果AirSpeed Velocity的答案对您不起作用,您也可以通过桥接到Objective-C来实现这一目标。
让GmBuilding
继承自NSObject
:
class GmBuilding: NSObject { }
并使用isKindOfClass(_:)
检查类型:
for building in self.buildings {
if building.isKindOfClass(buildingType) {
result.append(building)
}
}
不是很好,但它确实有效。
答案 2 :(得分:0)
我确信必须有比这更好的方法,但它不需要从NSObject继承并且它在运行时工作 - 根据我的操场
class GmBuilding { }
class GmOffice: GmBuilding { }
class GmFactory: GmBuilding { }
func thingIs(thing: GmBuilding, #sameTypeAs: GmBuilding) -> Bool
{
return thing.dynamicType === sameTypeAs.dynamicType
}
var foo: GmOffice = GmOffice()
thingIs(foo, sameTypeAs: GmOffice()) // true
thingIs(foo, sameTypeAs: GmFactory()) // false
我实例化一个对象的主要原因(你可以使用单例)是因为我无法弄清楚如何将参数声明为元类型。
它也不适用于
thingIs(foo, sameTypeAs: GmBuilding()) // false :=(
答案 3 :(得分:0)
作为最后的手段,使用Obj-C反映功能:
import ObjectiveC
func isinstance(instance: AnyObject, cls: AnyClass) -> Bool {
var c: AnyClass? = instance.dynamicType
do {
if c === cls {
return true
}
c = class_getSuperclass(c)
} while c != nil
return false
}
class GmBuilding { }
class GmOffice: GmBuilding { }
class GmFactory: GmBuilding { }
isinstance(GmOffice(), GmOffice.self) // -> true
isinstance(GmOffice(), GmFactory.self) // -> false
isinstance(GmOffice(), GmBuilding.self) // -> true