@@ -1862,7 +1862,7 @@ defmodule Module.Types.Descr do
1862
1862
if map_empty_negation? ( tag , acc_fields , neg ) do
1863
1863
{ acc_fields , acc_negs }
1864
1864
else
1865
- case map_all_but_one? ( tag , acc_fields , neg_tag , neg_fields ) do
1865
+ case map_all_but_one ( tag , acc_fields , neg_tag , neg_fields ) do
1866
1866
{ :one , diff_key } ->
1867
1867
{ Map . update! ( acc_fields , diff_key , & difference ( & 1 , neg_fields [ diff_key ] ) ) ,
1868
1868
acc_negs }
@@ -1913,19 +1913,20 @@ defmodule Module.Types.Descr do
1913
1913
end
1914
1914
1915
1915
# If all fields are the same except one, we can optimize map difference.
1916
- defp map_all_but_one? ( tag1 , fields1 , tag2 , fields2 ) do
1917
- keys1 = Map . keys ( fields1 )
1918
- keys2 = Map . keys ( fields2 )
1919
-
1920
- if { tag1 , tag2 } == { :open , :closed } or
1921
- :sets . from_list ( keys1 , version: 2 ) != :sets . from_list ( keys2 , version: 2 ) do
1922
- :no
1916
+ defp map_all_but_one ( tag1 , fields1 , tag2 , fields2 ) do
1917
+ with true <- { tag1 , tag2 } != { :open , :closed } ,
1918
+ true <- map_size ( fields1 ) == map_size ( fields2 ) ,
1919
+ keys = :maps . keys ( fields1 ) ,
1920
+ true <- Enum . all? ( keys , fn key -> is_map_key ( fields2 , key ) end ) ,
1921
+ 1 <-
1922
+ Enum . count_until (
1923
+ keys ,
1924
+ fn key -> Map . fetch! ( fields1 , key ) != Map . fetch! ( fields2 , key ) end ,
1925
+ _limit = 2
1926
+ ) do
1927
+ { :one , Enum . find ( keys , & ( Map . fetch! ( fields1 , & 1 ) != Map . fetch! ( fields2 , & 1 ) ) ) }
1923
1928
else
1924
- Enum . count ( keys1 , fn key -> Map . get ( fields1 , key ) != Map . get ( fields2 , key ) end )
1925
- |> case do
1926
- 1 -> { :one , Enum . find ( keys1 , & ( Map . get ( fields1 , & 1 ) != Map . get ( fields2 , & 1 ) ) ) }
1927
- _ -> :no
1928
- end
1929
+ _ -> :no
1929
1930
end
1930
1931
end
1931
1932
0 commit comments