2013-05-01 13 views
7

Ho un file YAML con alcune voci che assomigliano a questo:Come si analizza YAML in un hash/oggetto?

001: 
    :title: Some title 
    :description: Some body text maybe 
002: 
    :title: Some title 
    :description: Some body text maybe 

sto usando il seguente metodo Ruby per analizzare il file YAML in un insieme di oggetti che posso iterare:

def parse_yaml(file) 
    YAML::load(File.open(File.join(settings.yaml_folder, file))) 
end 

def use_yaml 
    @items = parse_yaml('items.yml') 
    @items.each do |item| 
    x = item[1][:title] 
    etc... 
    end 
end 

Ora, questo metodo funziona, ma trovo queer che ho bisogno di usare item[1][:title] per accedere agli attributi dell'oggetto che sto iterando. Come posso creare il mio file YAML o il mio codice di analisi per consentirmi di utilizzare lo standard più item[:title]?

risposta

8

E 'un hash. L'uscita è parse_yaml:

{ 1=> 
     { :title=>"Some title", 
     :description=>"Some body text maybe"}, 
    2=> { :title=>"Some title", 
     :description=>"Some body text maybe" } 
} 

E 'possibile utilizzare il metodo each_value in questo modo:

#... 
@items = parse_yaml('items.yml') 
@items.each_value do |item| 
    x = item[:title] 
    # ... etc 
end 

Recomend: YAML for Ruby

1

tuo YAML è la serializzazione di un hash in modo che si possa fare:

@items.each do |key, item| 
    #do something with item[:title] 
end 

o cambia le YAML per assomigliare:

- :title: blah 
    :description: description 
- :title: second title 
    :description: second description 

che si tradurrà in YAML.load restituisce un array.

3

Il problema sottostante è che il file YAML memorizza i dati come hash e tenta di accedervi come un array.

Per convertire i dati in formato di array:

--- 
- :title: Some title 
    :description: Some body text maybe 
- :title: Some title 
    :description: Some body text maybe 

anche interessante notare, la ragione si doveva usare item[1][:title] fare riferimento i tuoi articoli è che le chiavi 001 e 002 vengono convertiti in numeri interi YAML.load .

È possibile confermare questo IRB:

irb(main):015:0> YAML.load(File.open("./test.yml")) 
=> {1=>{:title=>"Some title", :description=>"Some body text maybe"}, 2=>{:title=>"Some title", :description=>"Some body text maybe"}}