Определение текущего элемента является последним элементом коллекции? - PullRequest
1 голос
/ 01 апреля 2011

Есть ли лучший способ узнать, является ли текущий элемент коллекции последним?

@oranges = Orange.all

@oranges.each_with_index do |o, current_index|
  puts @oranges.size == (current_index + 1) ? "Last element!" : "Get next element"
end

ИЛИ

@oranges.each do |o|
  puts @oranges.last == o ? "Last element!" : "Get next element"
end

Ответы [ 2 ]

3 голосов
/ 01 апреля 2011

Либо выглядит хорошо, но если вы серьезно задумывались о производительности, я провел несколько тестов:

require 'benchmark'
a = (1..1000).to_a

def first(a)
  a.each_with_index do |o,i|
    a.size == (i + 1)
  end
end

def first_cached(a)
  a_size = a.size
  a.each_with_index do |o,i|
    a_size == (i + 1)
  end
end

def second(a)
  a.each do |e|
    a.last == e
  end
end

def second_cached(a)
  a_last = a.last
  a.each do |e|
    a_last == e
  end
end

Benchmark.bm(7) do |x|
x.report("first") {10000.times {first(a)}}
x.report("first_cached") {10000.times{first_cached(a)}}
x.report("second") {10000.times{second(a)}}
x.report("second_cached") {10000.times{second_cached(a)}}
end

, которые вернулись:

             user     system      total        real
first    2.020000   0.010000   2.030000 (  2.024102)
first_cached  1.930000   0.000000   1.930000 (  1.947230)
second   1.920000   0.010000   1.930000 (  1.922338)
second_cached  1.350000   0.000000   1.350000 (  1.352786)

Итак, вторая версия, сразмер кэша дал лучшие результаты ... однако, если эти микропроцессоры не имеют значения, это не должно быть проблемой.

1 голос
/ 01 апреля 2011

Первое решение вообще работает?o - оранжевый, и у него нет метода size.

Вместо этого вы можете сделать:

@oranges.each_with_index do |o, current_index|
  puts current_index == @oranges.size - 1 ? "Last element!" : "Get next element"
end

Кроме того, оба подхода хороши.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...