您必须做什么才能让设置操作对自定义对象起作用?

What must you do to have set operations work on custom objects?

我做了一个小操场来对自定义对象的 Set 操作进行一些测试,但它们仍然失败,我不知道为什么。

class User: NSObject {
    let id: String
    init(id: String) {
        self.id = id
        super.init()
    }

    override var hashValue: Int {
        get {
            return id.hashValue
        }
    }

    override var description: String {
        get {
            return id
        }
    }
}


func ==(lhs: User, rhs: User) -> Bool {
    return lhs.hashValue == rhs.hashValue
}

然后,我做了两组User对象:

let user1 = User(id: "zach")
let user2 = User(id: "john")
let user3 = User(id: "shane")


let user4 = User(id: "john")
let user5 = User(id: "shane")
let user6 = User(id: "anthony")

let userSet1 : Set<User> = [user1, user2, user3]
let userSet2 : Set<User> = [user4, user5, user6]

但是当我这样操作的时候:

let newSet = userSet1.subtract(userSet2)
print(newSet)

newSet 等同于 userSet1 并且 none 的集合被修改。

我必须做什么才能使这些设置操作起作用?

id:zach -> 4799450060450308971
id:john -> 4799450060152454338
id:shane -> -4799450060637667915
id:john -> 4799450060152454338
id:shane -> -4799450060637667915
id:anthony -> 4799450059843449897
id:shane -> -4799450060637667915
id:anthony -> 4799450059843449897
id:john -> 4799450060152454338

您无法自行决定将什么用作散列值。 hashability的要求是:如果这两个对象相等.

,则两个对象的哈希值必须相同

您提供了一个哈希值算法,但您没有采取任何措施使您的用户对象的等同性与其相匹配。

这是一个在集合中可散列的用户对象:

func ==(lhs:User, rhs:User) -> Bool {
    return lhs.id == rhs.id
}
class User: Hashable, CustomStringConvertible {
    let id: String
    init(id: String) {
        self.id = id
    }
    var hashValue: Int {
        return id.hashValue
    }
}

请注意,我已经消除了使这个东西也成为 NSObject 的复杂性。如果您想这样做,情况会有所不同;您需要考虑 NSObject 的工作原理。