Как Рубиниус и JRuby могут быть такими медленными?

Я решил посмотреть, сколько времени потребуется, чтобы перебрать массив хешей. Ниже приведен код:

pairs = [{name: "firstname", value: "string"},{name: "lastname", value: "string"},{name: "country", value: "string"},{name: "city", value: "string"},{name: "state", value: "string"},{name: "company", value: "string"},{name: "year", value: "string"},{name: "political_affiliation", value: "string"},{name: "social_security_number", value: "string"}] * 1000
blank = {}

start = Time.now
pairs.each do |pair|
  blank[pair[:name]] = pair[:value]
end

p Time.now - start

Время рассчитывается путем вычитания текущего времени после цикла из текущего времени до цикла.

Это было количество времени, которое вычисление заняло в YARV 2.1.1, в соответствии с математикой в ​​коде:

0.001962017

Вот сколько времени потребовалось в Rubinius 2.2.6:

0.022598

И jRuby 1.7.12

0.022317

Предположительно Rubinius и jRuby имеют преимущества в производительности по сравнению с YARV. Почему для выполнения одной и той же базовой операции требуется почти в 12 раз больше времени? Это нормально или у меня что-то неправильно настроено?

1 ответ

Решение

Вы тестируете слишком малое количество раз, что скомпрометировано загрузкой среды. По моему опыту, для того, чтобы иметь надежные тесты, вы должны установить время не менее 10 секунд, чтобы уменьшить время прогрева. Примерно через 10 секунд я ожидаю, что JRuby будет наиболее производительным, а затем Руби и Рубиниус.

Посмотрим:

# so_24049371.rb

require 'benchmark'

# NOTE THIS: YOU SHOULD TWEAK IT IN ORDER TO HAVE BENCHMARKS OF ~ 10 SECONDS
MULTIPLIER = 5_000_000
pairs = [{name: "firstname", value: "string"},{name: "lastname", value: "string"},{name: "country", value: "string"},{name: "city", value: "string"},{name: "state", value: "string"},{name: "company", value: "string"},{name: "year", value: "string"},{name: "political_affiliation", value: "string"},{name: "social_security_number", value: "string"}] \
  * MULTIPLIER
blank = {}

puts Benchmark.measure {
  pairs.each do |pair|
    blank[pair[:name]] = pair[:value]
  end
}

# so_24049371.fish

source (rbenv init -|psub)

for ruby_version in 2.1.2 rbx-2.2.7 jruby-1.7.12
  rbenv shell $ruby_version
  ruby -v
  ruby so_24049371.rb
end

Это вывод на моей машине (я использую fish shell + rbenv, вы должны написать свой собственный скрипт):

> fish so_24049371.fish
ruby 2.1.2p95 (2014-05-08 revision 45877) [x86_64-linux]
  8.190000   0.000000   8.190000 (  8.188726)
rubinius 2.2.7 (2.1.0 build 2014-05-20 JI) [x86_64-linux-gnu]
 14.359762   0.003525  14.363287 ( 14.193565)
jruby 1.7.12 (2.0.0p195) 2014-04-15 643e292 on Java HotSpot(TM) 64-Bit Server VM 1.7.0_55-b13 [linux-amd64]
  4.570000   0.000000   4.570000 (  4.367000)

Как я и предполагал, JRuby является самым быстрым с 4.367000, чем Ruby с 8.188726 и последним Rubinius с 14.193565.

Другие вопросы по тегам