Reputation: 169
I'm using a 3rd party library that in my use case is handing me down a '[Any?]' array. This array contains equatable struct objects which are defined as follows:
struct SplitValue<L: Equatable, R: Equatable> {
public var left: L?
public var right: R?
public init(left: L?, right: R?){
self.left = left
self.right = right
}
}
extension SplitValue: Equatable {
public static func ==(lhs: SplitValue, rhs: SplitValue) -> Bool {
return lhs.left == rhs.left && lhs.right == rhs.right
}
}
And this is a simple example of the array I'm dealing with:
var values = [Any?]()
values.append(SplitValue<String, Int>(left: "a", right: 12))
values.append(SplitValue<Double, String>(left: 33.1, right: "b"))
Now let's say I cannot predict which value types are found in the SplitValue.left and SplitValue.right properties. It could be a String, Int, NSManagedObject, or anything else equatable. All I have is the values array.
Next I want to loop through this array and read out the left and right values. For this I believe I have to cast 'Any?' to 'SplitValue' because the following doesn't work:
print(values.first!.left)
// error: value of type 'Any?' has no member 'left'
I also tried things like this, but that obviously doesn't work either:
print(values.first! as SplitValue<Any, Any>)
// error: type 'Any' does not conform to protocol 'Equatable'
So the problem is that I can't cast 'Any?' to the right type since I don't know what it will be. What might be the solution to this, preferably without having to change the definition of the struct or values array?
Upvotes: 1
Views: 407
Reputation: 271775
What you can do is to create a protocol without the generic types and have SplitValue
implement that:
protocol AnySplitValue {
var l: Any? { get }
var r: Any? { get }
}
Then, conform SplitValue
to the protocol:
extension SplitValue: AnySplitValue {
var l: Any? {
return self.left
}
var r: Any? {
return self.right
}
}
Now, you can do this to print all the left values out:
values.forEach { print(($0 as! AnySplitValue).l!) }
We have kind of "erased" the generic types!
Upvotes: 3