Skip to content

Commit eff51e4

Browse files
committed
explicitly use Dict.size rather than just size in equal?
Fixes bug where `true` was incorrectly returned for `Dict.equal?` when the 1st argument was a subset of the 2nd argument. e.g: ```elixir iex> h1 = HashDict.new(foo: 1, bar: 2) iex> h2 = HashDict.new(foo: 1, bar: 2, baz: 3) iex> Dict.equal?(h1, h2) true # OOPS iex> Dict.equal?(h2, h1) false # works as expected other way round ``` The code to check equality was checking size (incorrectly), and then checking to see if every element in the first dict was present in the 2nd. However, `size` was being used instead of `Dict.size`. This ended up calling `Kernel.size` instead - and would always return `true` regardless of whever the actual size of the `Dict` arguments were the same or not.
1 parent ea5df22 commit eff51e4

File tree

2 files changed

+6
-2
lines changed

2 files changed

+6
-2
lines changed

lib/elixir/lib/dict/behaviour.ex

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,7 @@ defmodule Dict.Behaviour do
9999
defoverridable values: 1
100100

101101
def equal?(dict1, dict2) do
102-
case size(dict1) == size(dict2) do
102+
case Dict.size(dict1) == Dict.size(dict2) do
103103
false -> false
104104
true ->
105105
try do
@@ -122,4 +122,4 @@ defmodule Dict.Behaviour do
122122
defoverridable merge: 2, merge: 3
123123
end
124124
end
125-
end
125+
end

lib/elixir/test/elixir/dict_test.exs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -214,6 +214,10 @@ defmodule DictTest.Common do
214214

215215
dict2 = Dict.put(dict2, :a, 3)
216216
refute Dict.equal?(dict1, dict2)
217+
218+
dict3 = HashDict.new(a: 2, b: 3, f: 5, c: 123, z: 666)
219+
refute Dict.equal?(dict1, dict3)
220+
refute Dict.equal?(dict3, dict1)
217221
end
218222

219223
test "unsupported dict" do

0 commit comments

Comments
 (0)