fastruby / fast-ruby

:dash: Writing Fast Ruby :heart_eyes: -- Collect Common Ruby idioms.
https://github.com/fastruby/fast-ruby
5.67k stars 376 forks source link

Add Range#cover? versus Range#include? example #44

Closed JuanitoFatas closed 9 years ago

JuanitoFatas commented 9 years ago

Is this a good example?

tgxworld commented 9 years ago

:+1: :kissing_heart:

JuanitoFatas commented 9 years ago

:+1: :kissing_heart:

Thanks GX for your feedback!

gettalong commented 9 years ago

The example should probably be refined because it is misleading in certain cases. The difference is negligible when the range was built using integers or strings, see below.

Also Range#=== uses #include? and not #cover?. This should probably be mentioned, too, so that readers know when #cover? is faster.

require "benchmark/ips"
require "date"

BEGIN_OF_JULY = Date.new(2015, 7, 1)
END_OF_JULY = Date.new(2015, 7, 31)
DAY_IN_JULY = Date.new(2015, 7, 15)

def fast
  (BEGIN_OF_JULY..END_OF_JULY).cover? DAY_IN_JULY
end

def slow
  (BEGIN_OF_JULY..END_OF_JULY).include? DAY_IN_JULY
end

Benchmark.ips do |x|
  x.report("Date Range#cover?") { fast }
  x.report("Date Range#include?") { slow }
  x.compare!
end

def fast1
  (1..31).cover? 15
end

def slow1
  (1..31).cover? 15
end

Benchmark.ips do |x|
  x.report("Fixnum Range#cover?") { fast1 }
  x.report("Fixnum Range#include?") { slow1 }
  x.compare!
end

def fast2
  (('A').freeze..('Z'.freeze)).cover? 'M'.freeze
end

def slow2
  (('A').freeze..('Z'.freeze)).cover? 'M'.freeze
end

Benchmark.ips do |x|
  x.report("String Range#cover?") { fast2 }
  x.report("String Range#include?") { slow2 }
  x.compare!
end

Result:

Calculating -------------------------------------
   Date Range#cover?     60453 i/100ms
 Date Range#include?      5186 i/100ms
-------------------------------------------------
   Date Range#cover?  1452907.5 (±3.1%) i/s -    7314813 in   5.038892s
 Date Range#include?    54691.1 (±3.0%) i/s -     274858 in   5.029475s

Comparison:
   Date Range#cover?:  1452907.5 i/s
 Date Range#include?:    54691.1 i/s - 26.57x slower

Calculating -------------------------------------
 Fixnum Range#cover?    107883 i/100ms
Fixnum Range#include?
                        109969 i/100ms
-------------------------------------------------
 Fixnum Range#cover?  3895964.6 (±3.6%) i/s -   19526823 in   5.017561s
Fixnum Range#include?
                      4006796.3 (±5.3%) i/s -   20014358 in   5.008010s

Comparison:
Fixnum Range#include?:  4006796.3 i/s
 Fixnum Range#cover?:  3895964.6 i/s - 1.03x slower

Calculating -------------------------------------
 String Range#cover?     74770 i/100ms
String Range#include?
                         76861 i/100ms
-------------------------------------------------
 String Range#cover?  2268643.9 (±7.1%) i/s -   11365040 in   5.032739s
String Range#include?
                      2257703.5 (±6.8%) i/s -   11298567 in   5.025221s

Comparison:
 String Range#cover?:  2268643.9 i/s
String Range#include?:  2257703.5 i/s - 1.00x slower