2016-06-22 10 views
0

ich ein Array von Hashes haben:Ersetzen Hash-Wert

[{"__content__"=>"Guitars", "id"=>"2"}, 
{"__content__"=>"For Guitars", "id"=>"3", "parentId"=>"2"}, 
{"__content__"=>"6-string", "id"=>"24", "parentId"=>"2"}, 
{"__content__"=>"7-string", "id"=>"25", "parentId"=>"2"}, 
{"__content__"=>"8-string", "id"=>"26", "parentId"=>"2"}] 

ich die parentId Werte mit den __content__ Werte ersetzen wollen zu bekommen:

[{"__content__"=>"Guitars", "id"=>"2"}, 
{"__content__"=>"For Guitars", "id"=>"3", "parentId"=>"Guitars"}, 
{"__content__"=>"6-string", "id"=>"24", "parentId"=>"Guitars"}, 
{"__content__"=>"7-string", "id"=>"25", "parentId"=>"Guitars"}, 
{"__content__"=>"8-string", "id"=>"26", "parentId"=>"Guitars"}] 

Wie kann ich es tun?

+0

Also Wert von '__content__' muss in' parentId' gehen? – Roger

Antwort

4

Ich ziehe diese array-hash für eine bessere maping nasted zu ändern.

Eingang

arr = [ 
    {"__content__" => "Guitars", "id" => "2"}, 
    {"__content__" => "For Guitars", "id" => "3", "parentId" => "2"}, 
    {"__content__" => "6-string", "id" => "24", "parentId" => "2"}, 
    {"__content__" => "7-string", "id" => "25", "parentId" => "2"}, 
    {"__content__" => "8-string", "id" => "26", "parentId" => "2"} 
] 

erstellen Eltern

parents = arr.each_with_object({}) { |h, exp| exp[h['id']] = h['__content__'] } 

Nach dieser guten Map-Struktur können Sie einfach map Methode verwenden.

Prozess

output = arr.map do |h| 
    h['parentId'] = parents[h['parentId']] if h['parentId'] && parents[h['parentId']] 
    h 
end 

Ausgang

p output 

# [ 
# {"__content__" => "Guitars", "id" => "2"}, 
# {"__content__" => "For Guitars", "id" => "3", "parentId" => "Guitars"}, 
# {"__content__" => "6-string", "id" => "24", "parentId" => "Guitars"}, 
# {"__content__" => "7-string", "id" => "25", "parentId" => "Guitars"}, 
# {"__content__" => "8-string", "id" => "26", "parentId" => "Guitars"} 
# ] 

Ich hoffe, das hilft.

EDIT

Sie auch auf diese Weise

Art von ID verwenden können

arr.sort_by! { |h| h['id'] } 

Prozess

output = arr.each_with_object({}) do |h, exp| 
    exp[h['id']] = h 
    h['parentId'] = exp[h['parentId']]['__content__'] if h['parentId'] && exp[h['parentId']] 
    h 
    end 

danach werden Sie Hash mit id haben wie Schlüssel, so dass für die Ausgabe:

Ausgang

p output.values 

# [ 
# {"__content__"=>"Guitars", "id"=>"2"}, 
# {"__content__"=>"6-string", "id"=>"24", "parentId"=>"Guitars"}, 
# {"__content__"=>"7-string", "id"=>"25", "parentId"=>"Guitars"}, 
# {"__content__"=>"8-string", "id"=>"26", "parentId"=>"Guitars"}, 
# {"__content__"=>"For Guitars", "id"=>"3", "parentId"=>"Guitars"} 
# ] 
+0

, es funktioniert. Ziemlich komplex, aber im Allgemeinen hat es getan, was ich brauche. thx – user

+0

Ich uploated, habe aber zwei Vorschläge zur Verbesserung Ihrer Antwort. Erstens, wenn Sie die Lösung präsentieren, die Sie verwenden würden, würde eine minderwertige Alternative (hier die, die 'sort' verwendet) Ihre Antwort schwächen. (Wenn es zwei Möglichkeiten gibt, etwas zu tun, das keinen klaren Gewinner hat, dann stelle sie beide vor.) Zweitens denke ich, dass die meisten Leser den gesamten Code an einem Ort sehen möchten, anstatt ihn mit Erklärungen zu bauen. Sie können entweder zuerst den Code eingeben und dann die Schritte erläutern (welche Leser den Code verstehen) oder die Schritte in Worten ausführen, bevor Sie den Code präsentieren. –

+0

@CarySwoveland Vielen Dank für Ihre Vorschläge.Ich werde versuchen, meine Antworten zu verbessern. –

0
arr = [{"__content__"=>"Guitars", "id"=>"2"}, {"__content__"=>"For Guitars", "id"=>"3", "parentId"=>"2"}] 

id_content_mapping = arr.reduce({}) do |h, elt| 
    h[elt["id"]] = elt["__content__"] 
    h 
end 

arr.map do |elt| 
    if elt.has_key? "parentId" 
    elt["parentId"] = id_content_mapping[elt["parentId"]] 
    end 
    elt 
end 
1

Vorsicht! Die folgende Lösung mutiert den ursprünglichen Hash!

▶ hashes = [{"__content__"=>"Guitars", "id"=>"2"}, 
▷ {"__content__"=>"For Guitars", "id"=>"3", "parentId"=>"2"}, 
▷ {"__content__"=>"6-string", "id"=>"24", "parentId"=>"2"}, 
▷ {"__content__"=>"7-string", "id"=>"25", "parentId"=>"2"}, 
▷ {"__content__"=>"8-string", "id"=>"26", "parentId"=>"2"}] 

hashes.each_with_object({}) do |h, memo| 
    memo[h['id']] = h['__content__'] 
    h['parentId'] = memo[h['parentId']] 
end 

hashes 
#⇒ [{"__content__"=>"Guitars", "id"=>"2", "parentId"=>nil}, 
# {"__content__"=>"For Guitars", "id"=>"3", "parentId"=>"Guitars"}, 
# {"__content__"=>"6-string", "id"=>"24", "parentId"=>"Guitars"}, 
# {"__content__"=>"7-string", "id"=>"25", "parentId"=>"Guitars"}, 
# {"__content__"=>"8-string", "id"=>"26", "parentId"=>"Guitars"}] 
+1

Das ist ein interessanter Name für ein Array. –

+0

@CarySwoveland Ich liebe es zu verwickeln! – mudasobwa

+0

Ich habe es bemerkt. Ich bin von Kritik gequetscht. –