Должен быть более чистый способ сделать это - PullRequest
1 голос
/ 09 октября 2010

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

[ 
{
  "Vector Arena - Auckland Central, New Zealand" => { 
    "2010-10-10" => [
       "Enter Sandman", 
       "Unforgiven", 
       "And justice for all"
    ]
  }
},  
{
  "Brisbane Entertainment Centre - Brisbane Qld, Austr..." => { 
    "2010-10-11" => [
      "Enter Sandman"
    ]
  }
}
]

один для прошлого и один для будущего ... у меня проблема в том, что я повторяюсь, и хотя это работает, я хочу очистить это ... вот мои данные ..

1 Ответ

1 голос
/ 09 октября 2010

Попробуйте:

h = Hash.new {|h1, k1| h1[k1] = Hash.new{|h2, k2| h2[k2] = []}}
result, today = [ h, h.dup], Date.today

Request.find_all_by_artist("Metallica", 
 :select => "DISTINCT venue, showdate, LOWER(song) AS song"
).each do |req|
  idx = req.showdate < today ? 0 : 1
  result[idx][req.venue][req.showdate] << req.song.titlecase
end

Примечание 1

В первой строке я инициализирую хэш хэшей.Внешний хеш создает внутренний хеш при обращении к несуществующему ключу.Выдержка из Ruby Hash документации :

If this hash is subsequently accessed by a key that doesn‘t correspond to a hash 
entry, the block will be called with the hash object and the key, and should 
return the default value. It is the block‘s responsibility to store the value in 
the hash if required. 

Внутренний хеш создает и очищает массив при обращении к несуществующей дате.

Например: Создайте хеш, содержащийсодержимое в виде значений и дата в виде ключей:

без блока по умолчанию:

h = {}
list.each do |data|
  h[data.date] = [] unless h[data.date]
  h[data.date] << data.content
end

с блоком по умолчанию

h = Hash.new{|h, k| h[k] = []}
list.each do |data|
  h[data.date] << data.content
end

Вторая строка просто создает массив из двух элементовхранить прошлые и будущие данные.Так как данные прошлого и настоящего хранят данные как Hash of Hash of Array, я просто дублирую значение.

Вторая строка также может быть записана как

result = [ h, h.dup]
today = Date.today
...