Skip to content

Commit

Permalink
fix #6870, hashing collections
Browse files Browse the repository at this point in the history
  • Loading branch information
JeffBezanson committed May 19, 2014
1 parent 18d1266 commit 00081d7
Show file tree
Hide file tree
Showing 2 changed files with 19 additions and 3 deletions.
11 changes: 8 additions & 3 deletions base/hashing2.jl
Original file line number Diff line number Diff line change
Expand Up @@ -166,14 +166,19 @@ hash(s::String, h::Uint) = hash(bytestring(s), h)

## hashing collections ##

function hash(v::Union(Tuple,AbstractArray,Associative), h::Uint)
h += object_id(eltype(v))
for x = v
function hash(v::Union(AbstractArray,Associative), h::Uint)
h += uint(isa(v,Associative) ? 0x6d35bb51952d5539 : 0x7f53e68ceb575e76)
for x in v
h = hash(x, h)
end
return h
end

hash(::(), h::Uint) = h + uint(0x77cfa1eef01bca90)
hash(x::(Any,), h::Uint) = hash(x[1], hash((), h))
hash(x::(Any,Any), h::Uint) = hash(x[1], hash(x[2], hash((), h)))
hash(x::Tuple, h::Uint) = hash(x[1], hash(x[2], hash(tupletail(x), h)))

hash(s::Set, h::Uint) = hash(sort(s.dict.keys[s.dict.slots .!= 0]), h)

hash(r::Range{Bool}, h::Uint) = invoke(hash, (Range, Uint), r, h)
Expand Down
11 changes: 11 additions & 0 deletions test/hashing.jl
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,17 @@ for T=types, S=types, x=vals
# end
end

# hashing collections (e.g. issue #6870)
vals = {[1,2,3,4], [1 2;3 4], {1,2,3,4}, [1,3,2,4],
Set([1,2,3,4]),
[42 => 101, 77 => 93], {42 => 101, 77 => 93},
(1,2,3,4), (1.0,2.0,3.0,4.0), (1,3,2,4),
("a","b"), (SubString("a",1,1), SubString("b",1,1))}

for a in vals, b in vals
@test !isequal(a,b) || hash(a)==hash(b)
end

@test hash(RopeString("1","2")) == hash("12")
@test hash(SubString("--hello--",3,7)) == hash("hello")
@test hash(:(X.x)) == hash(:(X.x))
Expand Down

1 comment on commit 00081d7

@StefanKarpinski
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is of course still an issue:

julia> hash([1, 2, 3, 4])
0x400907b78bc63790

julia> hash([1 3; 2 4])
0x400907b78bc63790

Please sign in to comment.