我正在從網站上刮取以下數據的網絡抓取工具。如何將數據保存到多維Ruby哈希,然後將哈希轉換爲單個JSON文件?
- 集團
- 類別
- 搜索屬性
我用下面的代碼保存數據爲三個獨立的(一維)JSON文件:
require 'mechanize'
@raw_groups_array = []
@raw_categories_array = []
@search_attributes = []
@groups_clean = []
@categories_clean = []
@categories_combined = []
@categories_hash = {}
# Initialize Mechanize object
a = Mechanize.new
# Begin magic
a.get('http://www.marktplaats.nl/') do |page|
groups = page.search('//*[(@id = "navigation-categories")]//a')
groups.each do |group|
@raw_groups_array.push(group)
@groups_clean.push(group.text)
a.get(group[:href]) do |page_2|
categories = page_2.search('//*[(@id = "category-browser")]//a')
categories.each do |category|
@raw_categories_array.push(category)
@categories_clean.push(category.text)
@categories_combined.push("#{group.text} | #{category.text}")
a.get(category[:href]) do |page_3|
search_attributes = page_3.search('//*[contains(concat(" ", @class, " "), concat(" ", "heading", " "))]')
search_attributes.each do |attribute|
@search_attributes.push("#{group.text} | #{category.text} | #{attribute.text}") unless attribute.text == 'Outlet '
# Uncomment the line below if you want to see what's going on.
# (it has minimal effect on performance)
puts "#{group.text} | #{category.text} | #{attribute.text}" unless attribute.text == 'Outlet '
end
end
end
end
end
end
# Write json files
File.open('json/prestige/prestige_groups.json', 'w') do |f|
puts '# Writing groups'
f.write(@groups_clean.to_json)
puts '|-----------> Done.'
end
File.open('json/prestige/prestige_categories.json', 'w') do |f|
puts '# Writing categories'
f.write(@categories_clean.to_json)
puts '|-----------> Done.'
end
File.open('json/prestige/prestige_combined.json', 'w') do |f|
puts '# Writing combined'
f.write(@categories_combined.to_json)
puts '|-----------> Done.'
end
File.open('json/prestige/prestige_search_attributes.json', 'w') do |f|
puts '# Writing search attributes'
f.write(@search_attributes.to_json)
puts '|-----------> Done.'
end
puts '# Finished.'
代碼起作用。但我有一個很難重構它採用以下格式創建Ruby哈希:
{
"category"=>{
"name"=>"#{category}",
"group"=>"#{group}",
"search_attributes"=>{
"1"=>"#{search_attributes[0]}",
"2"=>"#{search_attributes[1]}",
"."=>"#{search_attributes[.]}",
"i"=>"#{search_attributes[i]}", # depending on search_attributes.length
}
}
}
我已經試過了諸如:
...
search_attributes.each do |attribute|
@categories_hash.store([:category][:name], category.text)
@categories_hash.store([:category][:group], group.text)
@categories_hash.store([:category][:search_attributes][:1], attribute.text)
end
...
但不斷收到語法錯誤。
任何幫助,將不勝感激。
更新
馬克斯建議我嘗試Hash#[]
但這返回一個哈希與單一類別(最後一個)。
search_attributes.each_with_index do |attribute, index|
@categories_hash[:category][:name] = category.text
@categories_hash[:category][:group] = group.text
@categories_hash[:category][:search_attributes][:"#{index}"] = attribute.text unless attribute.text == "Outlet "
end
我已粘貼完整密碼here。
我不認爲你瞭解混編工作。哈希中的每個密鑰必須是唯一的。 ':category'是一個Symbol,所以你每次都覆蓋最後一個值。根據你最初的嘗試,它看起來並不像你對Ruby的語法有很強的把握。 – Max
因此我問的問題。我需要幫助。這是SO的目的。 – narzero
我明白,但它看起來太寬泛了。我不清楚你的誤解在哪裏,所以我想不出一個解決它的單一答案。任何體面的Ruby教程都應該涵蓋這些基礎知識。 – Max