Pan y Queso equality in Swift
Sat, 20 Aug 2016 18:49:45 +0100
Structs in Swift are copied by value, while classes are copied by reference. If we want to check if the reference of an object is the same, we can use the triple equality operator. From Apple's book “The Swift Programming Language”,

Swift also provides two identity operators (=== and !==), which you use to test whether two object references both refer to the same object instance.

I've put here a few examples that you can copy-paste into a Playground to understand what the above means when using comparison operators:

struct Pan {
    let rating : Int
}
class Queso {
    let rating : Int
    init(rating: Int) {
        self.rating = rating
    }
}
var q1 = Queso(rating: 0)
var q2 = Queso(rating: 0)
var q3 = q1 // same reference
var q4 = Queso(rating: 1)
q1 == q2 // error, == not defined
q1 === q2 // false
q3 === q1 // true
var p1 = Pan(rating: 0)
var p2 = Pan(rating: 0)
p1 == p2 // error, == not defined
p1 === p2 // error, they aren't references!
let quesos = [q1, q2]
quesos.contains(q1) // error, can't convert q1 to predicate
quesos.contains { $0 === q1 } // true
quesos.contains { $0 === q3 } // true
quesos.contains { $0 === q4 } // false

We can define an equality function if we want to check for the equality of the Pan and Queso values,

func ==(lhs: Pan, rhs: Pan) -> Bool {
    return lhs.rating == rhs.rating
}
p1 == p2 // true
func ==(lhs: Queso, rhs: Queso) -> Bool {
    return lhs.rating == rhs.rating
}
q1 == q2 // true
q1 == q4 // false
quesos.contains(q1) // still an error! pass a predicate

If we want to be able to pass a Queso to the "contains" or "indexOf" methods of array, we have to conform to the Equatable protocol. Having the equality function alone doesn't work. This will work,

class Queso : Equatable {
    let rating : Int
    init(rating: Int) {
        self.rating = rating
    }
}
func ==(lhs: Queso, rhs: Queso) -> Bool {
    return lhs.rating == rhs.rating
}
// ...
quesos.contains(q1) // true

Happy coding!

Relevant StackOverflow questions:


Newer|Older

Previous year

Next year