2013-05-01 2 views
-2

У меня есть многострочная форма с полями product_id, quantity, price, address. В форме могут быть определенные пользователем строки. Я хочу сгруппировать эти записи с помощью уникальных адресов.Группировка с помощью ключа в хеше

form_details=params делает form_details что-то вроде:

form_details = { 
    :product_id => [1,2,3,4,5], 
    :quantity => [10,20,30,40,6], 
    :price => [100,1000,200,30,2000], 
    :address =>[ 'x','y','z','x','y'] 
} 

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

result = { 
    :product_id => [1,4], 
    :quantity => [10,40], 
    :price => [100,30], 
    :address => ['x'] 
} 

Во второй раз все детали должны быть сгруппированы по address=>'y'

, а затем третий и последний раз на address=>'z'.

Каков наилучший способ для этого?

+0

откуда «заказ» приходит? это 'order =>' или 'order ='? –

+0

Просто возьмите его как новую переменную ... Результат должен храниться в порядке каждый раз. –

+1

@MrYoshiji, пожалуйста, не изменяйте примеры кода в вопросе OP. Это считается плохой редакцией и требует откат. Только ОП должен изменить свой код. Сделать его читабельным - это одно, но не меняйте его содержание. –

ответ

1

Не слишком шикарно, но вот одно решение:

input = {:product_id => [1,2,3,4,5],:quantity=>[10,20,30,40,6],:price=>[100,1000,200,30,2000],:address=>['x','y','z','x','y']} 

output = Hash.new do |h, k| 
    h[k] = Hash.new do |h, k| 
    h[k] = [] 
    end 
end 

input[:address].each_with_index do |address, index| 
    input.each do |key, value| 
    next if key == :address 
    output[address][key] << value[index] 
    end 
end 

p output 

Выход:

{"x"=>{:product_id=>[1, 4], :quantity=>[10, 40], :price=>[100, 30]}, "y"=>{:product_id=>[2, 5], :quantity=>[20, 6], :price=>[1000, 2000]}, "z"=>{:product_id=>[3], :quantity=>[30], :price=>[200]}} 

Hash.new устанавливает полезные значения по умолчанию для ключей хэша, которые не установлены, поэтому мы не имеем помещать в ||= всюду.

Логика проста: Для каждого индекса :address массива, нажмите index-е значения всех ключей, кроме :address из input в output.

+0

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

+0

Один вопрос, что это делает точно => output = Hash.new do | h, k | h [k] = Хеш.new do | h, k | h [k] = [] конец конец ..... Если бы мы только что сделали = {}, это совсем другое? –

Смежные вопросы