1
0
Fork 0
mirror of https://github.com/ruby/ruby.git synced 2022-11-09 12:17:21 -05:00

Use faster any_hash logic in rb_hash

From the documentation of rb_obj_hash:

> Certain core classes such as Integer use built-in hash calculations and
> do not call the #hash method when used as a hash key.

So if you override, say, Integer#hash it won't be used from rb_hash_aref
and similar. This avoids method lookups in many common cases.

This commit uses the same optimization in rb_hash, a method used
internally and in the C API to get the hash value of an object. Usually
this is used to build the hash of an object based on its elements.
Previously it would always do a method lookup for 'hash'.

This is primarily intended to speed up hashing of Arrays and Hashes,
which call rb_hash for each element.

    compare-ruby: ruby 3.0.1p64 (2021-04-05 revision 0fb782ee38) [x86_64-linux]
    built-ruby: ruby 3.1.0dev (2021-09-29T02:13:24Z fast_hash d670bf88b2) [x86_64-linux]
    # Iteration per second (i/s)

    |                 |compare-ruby|built-ruby|
    |:----------------|-----------:|---------:|
    |hash_aref_array  |       1.008|     1.769|
    |                 |           -|     1.76x|
This commit is contained in:
John Hawthorn 2021-09-28 19:13:24 -07:00 committed by Aaron Patterson
parent 529fc204af
commit bb488a1a7f
Notes: git 2021-10-01 05:07:19 +09:00
2 changed files with 35 additions and 29 deletions

View file

@ -0,0 +1,5 @@
h = {}
arrays = (0..99).each_slice(10).to_a
#STDERR.puts arrays.inspect
arrays.each { |s| h[s] = s }
200_000.times { arrays.each { |s| h[s] } }