Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why doesn’t [Int] conform to Hashable in Swift 4.1?

Tags:

swift

With Swift 4.1 (Xcode 9.3) I’m trying to create a Set of [Int], but I get:

Type '[Int]' does not conform to the protocol 'Hashable'

But as far as I can tell https://swift.org/blog/conditional-conformance/ says that Array now conforms to Hashable whenever its values conform to Hashable. As a workaround I have:

extension Array: Hashable where Element == Int {
    public var hashValue: Int {
        return debugDescription.hashValue
    }
}

But I’m still wondering why I don’t get Hashable for free.

like image 479
Justin Garcia Avatar asked Dec 01 '25 00:12

Justin Garcia


1 Answers

Automatic synthesis of Hashable for arrays of Hashable elements is implemented in Swift 4.2. Automatic synthesis of Equatable for arrays of Equatable elements is implemented in Swift 4.1.

This seems to be misleading in the referenced blog entry, but is listed clearly in the Swift CHANGELOG:

Swift 4.2

The standard library types Optional, Array, ArraySlice, ContiguousArray, Dictionary, DictionaryLiteral, Range, and ClosedRange now conform to the Hashable protocol when their element or bound types (as the case may be) conform to Hashable. This makes synthesized Hashable implementations available for types that include stored properties of these types.

Swift 4.1

The standard library types Optional, Array, ArraySlice, ContiguousArray, and Dictionary now conform to the Equatable protocol when their element types conform to Equatable. This allows the == operator to compose (e.g., one can compare two values of type [Int : [Int?]?] with ==), as well as use various algorithms defined for Equatable element types, such as index(of:).

This is also discussed in Let Optional, Dictionary and Array conditionally conform to Hashable in the Swift forum:

When synthesizing Hashable I noticed that Array, Optional and Dictionary do not conditionally conform to Hashable, while Set (unconditionally) does.

Note however that the ability to define conditional conformance to a protocol is available in Swift 4.1, so you can generalize your extension to

#if swift(>=4.2)
#else
extension Array: Hashable where Element: Hashable {
    public var hashValue: Int {
        // ... whatever ...
    }
}
#endif
like image 81
Martin R Avatar answered Dec 07 '25 19:12

Martin R



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!