I need container for Any Equatable
items in NOT Generic
class (for example UI classes initial from storyboard). I need like this
var items: [Equatable]?
but it don't work, Equatable
need Generic. the problem that there is no exist common Equatable
class.
Ok - Go to generic! But if I do this
class Item<Value: Equatable>: Equatable {
var value: Value
init(_ value: Value) {
self.value = value
}
//Equatable
public static func ==(lhs: Item, rhs: Item) -> Bool {
return (lhs.value == rhs.value)
}
}
then I will be forced to specify the type in my nonGeneric-UI class. Like this
var items: [Item<WhatShouldBeHere?>]?
but again we come to the problem that there is no exist common Equatable
class
Any solutions for container for All Equatable?
In lieu of existential types, you need to use a type eraser:
public struct AnyEquatable: Equatable {
public let value: Any
private let equals: (Any) -> Bool
public init<E: Equatable>(_ value: E) {
self.value = value
self.equals = { ($0 as? E) == value }
}
public static func == (lhs: AnyEquatable, rhs: AnyEquatable) -> Bool {
return lhs.equals(rhs.value) || rhs.equals(lhs.value)
}
}
example usage:
let items = [
AnyEquatable(1),
AnyEquatable(1.23),
AnyEquatable(true),
AnyEquatable("some string")
]
let desired = "some string"
let desiredAsAnyEquatable = AnyEquatable(desired)
let desiredDescription = String(reflecting: desired)
for item in items {
let itemDescription = String(reflecting: item.value)
let isEqualToDesired = item == desiredAsAnyEquatable
print("\(itemDescription) is \(isEqualToDesired ? "": "not ")equal to \(desiredDescription)")
}
Example output:
1 is not equal to "some string"
1.23 is not equal to "some string"
true is not equal to "some string"
"some string" is equal to "some string"
来源:https://stackoverflow.com/questions/46288560/common-equatable-class-on-swift