2013-06-22 4 views
1

Я создаю пустой хэш chickens, а пары ключ-значение затем добавляются с течением времени.Есть ли простой способ итерации через пары в хеше Ruby в порядке добавления (т. Е. Самый старый)?

chickens = {} 
chickens.merge!("Davison"=>"plucky") 
chickens.merge!("Mortimer"=>"sullen") 
chickens.merge!("Chauncey"=>"forlorn") 

for name,mood in chickens do puts "#{name}: #{mood}" end 

производит

Mortimer: sullen 
Chauncey: forlorn 
Davison: plucky 

, но я не хочу этого. Как мне перебирать кур в том порядке, в котором они были добавлены?

ответ

2

Короткий ответ: обновите свой Ruby. Ruby 1.9 лет и работает так, как вы хотите (как и текущий Ruby, 2.0). Если вы настаиваете на древнем, неподдерживаемый Ruby, есть класс OrderedHash доступны через перл:

gem install orderedhash 

Ваш код будет затем стать:

require 'rubygems' 
require 'orderedhash' 

chickens = OrderedHash.new 
# The rest stays the same 

Опять же, я рекомендую вместо того, чтобы просто модернизировать установку Ruby.

P.S. Ваш код будет гораздо рубин, как если бы вы перебрать Hash, как это:

chickens.each do |name, mood| 
    puts "#{name}: #{mood}" 
end 
+0

Я не знал, что мой Ruby был старым! Я использую CodeAcademy Labs, который, как я предполагал, будет актуальным. Знаете ли вы о другом сайте, который имеет текущий Ruby? Кроме того, вам не обязательно быть таким скупым. Очевидно (из вопроса, который я задал), я очень новичок в этом, и, очевидно, я хочу использовать текущую поддерживаемую версию! – user2493615

+7

Я не вижу здесь никакой подлости. Просто прямое дело. –

+0

Дело в том, почему кто-нибудь, особенно полный нуб, который задал бы такой вопрос, как я спросил, «настаивайте на использовании древнего, неподдерживаемого Ruby»? Он знал, что я использую это по ошибке, и не знал ничего лучшего. Как он не мог? – user2493615

0

@DarshanComputing начал говорить о том, чтобы код более рубин, как, но вот как я бы образец кода в его цельность:

chickens = {} 
chickens["Davison"] = "plucky" 
chickens["Mortimer"] = "sullen" 
chickens["Chauncey"] = "forlorn" 

chickens.each do |name, mood| 
    puts "#{name}: #{mood}" 
end 

Использование merge это хорошо, но это также многословным. Вы увидите, что многие программисты Ruby используют более простой путь и добавляют пару ключ/значение напрямую, вместо того, чтобы полагаться на мутирующий метод.

Использование for для перебора чего-то определенно не похоже на Ruby. Несмотря на то, что язык поддерживает его, его использование игнорируется разработчиками Ruby. Причина в том, что for name, mood ... добавляет name и mood к локальным переменным, в отличие от each, который ограничивает их внутри блока do. Затухание пространства переменных временными переменными является плохим. Например, после запуска исходного кода я могу сделать:

[7] (pry) main: 0> name 
"Chauncey" 
[8] (pry) main: 0> mood 
"forlorn"