Ruby 2.4 changes overview

December 25, 2016

Unified Fixnum and Bignum into Integer

It’s backward compatible too.

$ irb
irb(main):001:0> RUBY_VERSION
=> "2.3.1"
irb(main):002:0> (2**100).class
=> Bignum
irb(main):003:0> 2.class
=> Fixnum
irb(main):004:0> Fixnum
=> Fixnum
irb(main):005:0> Bignum
=> Bignum
irb(main):006:0> Bogonum
NameError: uninitialized constant Bogonum
        from (irb):6
        from /home/spotter/.nix-profile/bin/irb:11:in `<main>'
irb(main):007:0> quit
$ nix-env -f . -iA ruby_2_4_0
replacing old ‘ruby-2.3.1-p0’
installing ‘ruby-2.4.0’
$ irb
irb(main):001:0> RUBY_VERSION
=> "2.4.0"
irb(main):002:0> (2**100).class
=> Integer
irb(main):003:0> 2.class
=> Integer
irb(main):004:0> Fixnum
(irb):4: warning: constant ::Fixnum is deprecated
=> Integer
irb(main):005:0> Bignum
(irb):5: warning: constant ::Bignum is deprecated
=> Integer
irb(main):006:0> Bogonum
NameError: uninitialized constant Bogonum
        from (irb):6
        from /home/spotter/.nix-profile/bin/irb:11:in `<main>'
irb(main):007:0> quit

Array#min/Array#max optimization in Ruby v2.4.0+

# content of ruby_array_benchmarks.rb
require 'benchmark'

LARGE_ARRAY = (1..100_000_000).to_a.freeze

puts "Ruby v#{RUBY_VERSION}"

Benchmark.bm(100) do |b|
  b.report('Array#min on large array') do
    LARGE_ARRAY.min
  end

  b.report('Array#max on large array') do
    LARGE_ARRAY.max
  end
end

Now let’s run this in 2.3.3 and 2.4.0 (scroll to right):

$ mv ruby_2_4_0_benchmarks.rb ruby_array_benchmarks.rb

$ ruby ruby_array_benchmarks.rb
Ruby v2.3.3
                                                                              user     system      total        real
Array#min on large array                                                  4.670000   0.000000   4.670000 (  4.673932)
Array#max on large array                                                  4.650000   0.000000   4.650000 (  4.644266)

$ nix-env -f . -iA ruby_2_4_0
replacing old ‘ruby-2.3.3’
installing ‘ruby-2.4.0’

$ ruby ruby_array_benchmarks.rb
Ruby v2.4.0
                                                                              user     system      total        real
Array#min on large array                                                  0.170000   0.000000   0.170000 (  0.169169)
Array#max on large array                                                  0.180000   0.000000   0.180000 (  0.186183)

Quite impressive improvement. Not sure how relevant it will be in the wilds of Ruby servers in production though.

There are other changes, which I haven’t had time to check out yet.

Note: the 2.3.3 build I used above to compare benchmarks to has RVM Railsexpress patches applied. The 2.4.0 version does not have the additional GC stats patch applied.