[swift-evolution] Pluggable hash algorithm for containers

Dmitri Gribenko gribozavr at gmail.com
Fri Dec 4 13:00:17 CST 2015


On Fri, Dec 4, 2015 at 10:45 AM, Ray Fix <rayfix at gmail.com> wrote:
>
>> On Dec 3, 2015, at 8:29 PM, Dmitri Gribenko <gribozavr at gmail.com> wrote:
>>
>> A prototype is here (written before Howard's talk, so it probably uses
>> different terms):
>>
>> https://github.com/apple/swift/blob/master/validation-test/stdlib/HashingPrototype.swift
>>
>
> Thank your for the excellent pointer, Dmitri.  I will look into that as I get setup to build, test, and make actual changes.
>
>> However, I couldn't make it interoperate with NSObject.hash in both
>> directions: you should be able to override 'var hash' and get an
>> implementation of Hashable based on that, and vice versa.  It could be
>> solvable with protocol extensions now, I haven't looked at that
>> prototype for more than a year -- help and patches appreciated.
>>
>
> As you know, a hashing algorithm just needs to consume raw bytes.  The HasherType protocol could use protocol extensions to provide a clean API to standard types like Int and Float, Double, String, Bool, UInt32, Sequences, etc.
>
> extension CGPoint : NewHashable {
>   func combineInto(hasher: Hasher) {
>     x.combineInto(hasher)
>     y.combineInto(hasher)
>   }

I definitely agree.

> What would be even better is if there was some interspection with a default implementation so the user code could look like this:
>
> extension CGPoint : NewHashable {}
>
> but that is dependent on another language feature.

Right, there are a lot of interesting things we could do if we had
more introspection language features.

> The default implementation of hash is to call combineInto(Hasher) with a legacy hasher and immediately squeeze.  Might even want this to be statically dispatched (an extension with no protocol definition).
>
> extension NewHashable {
>     var hash: Int {
>          var h = LegacyHasher()
>          self.combineInto(h)
>          return h.squeezeHashValue()
>     }
> }
>
> Any thoughts?

The interop issue is the following.  Consider a subclass of NSObject,
possibly defined in Objective-C, that does not conform to NewHashable:
we want to use its 'hash' implementation.  If someone subclasses
NSObject in Swift and implements NewHashable, we should use its API
instead.  If someone further subclasses that Swift class in
Objective-C, they should be able to add more properties, and override
'var hash', since that's the only API available in Objective-C.

Dmitri

-- 
main(i,j){for(i=2;;i++){for(j=2;j<i;j++){if(!(i%j)){j=0;break;}}if
(j){printf("%d\n",i);}}} /*Dmitri Gribenko <gribozavr at gmail.com>*/


More information about the swift-evolution mailing list