Skip to content

Instantly share code, notes, and snippets.

@michael-harrison
Last active August 29, 2015 13:57
Show Gist options
  • Save michael-harrison/9740103 to your computer and use it in GitHub Desktop.
Save michael-harrison/9740103 to your computer and use it in GitHub Desktop.
Hash to hash, dust to dust, experiment we must

Just had a quick look at the Ruby source and it looks like it doesn't compare the hash but uses the key object's == method to identify the right key. So to test the theory I did some experiments:

2.0.0-p247 :010 > test = {}
 => {} 
2.0.0-p247 :011 > a = [1,2]
 => [1, 2] 
2.0.0-p247 :012 > test[a]
 => nil 
2.0.0-p247 :013 > test[a] = 'cool'
 => "cool" 
2.0.0-p247 :014 > test[a]
 => "cool" 
2.0.0-p247 :015 > a = [1,2,3]
 => [1, 2, 3] 
2.0.0-p247 :016 > test[a]
 => nil 
2.0.0-p247 :017 > a = [1,2]
 => [1, 2] 
2.0.0-p247 :018 > test[a]
 => "cool" 

The reason why we get the nil is because [1,2] ==[1,2,3] is false. Another experiment with ActiveRecord using 2 models and 2 records with the same id:

2.0.0-p247 :019 > test = {}
 => {} 
2.0.0-p247 :020 > test[Role.first] = "foo"
  Role Load (0.3ms)  SELECT `roles`.* FROM `roles` LIMIT 1
 => "foo" 
2.0.0-p247 :021 > test[User.first] = "bar"
  User Load (0.3ms)  SELECT `users`.* FROM `users` LIMIT 1
 => "bar" 
2.0.0-p247 :022 > test[Role.first]
  Role Load (0.3ms)  SELECT `roles`.* FROM `roles` LIMIT 1
 => "foo" 
2.0.0-p247 :023 > test[User.first]
  User Load (0.3ms)  SELECT `users`.* FROM `users` LIMIT 1
 => "bar" 
2.0.0-p247 :024 > Role.first.hash
  Role Load (0.3ms)  SELECT `roles`.* FROM `roles` LIMIT 1
 => 2650587815033366890 
2.0.0-p247 :025 > User.first.hash
  User Load (0.5ms)  SELECT `users`.* FROM `users` LIMIT 1
 => 2650587815033366890 

So in each experiment the hash identifies the right key not by the key object’s hash but by it’s == method.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment