【发布时间】:2016-09-14 18:30:18
【问题描述】:
我是 ruby 和 json 的新手,所以可能以错误的方式处理这个问题。
我想获取一个以管道分隔格式的清单并将其转换为 json。
我已经尝试过这里的示例Convert csv to json in ruby
但是我有点纠结于逻辑,因为数据采用平面格式,将转换为嵌套列中的值匹配,例如 csv 文件将如下所示:-
id|shelf|package|price
cupboarda|shelf1|can1|10
cupboarda|shelf1|box1|20
cupboarda|shelf2|can1|10
cupboarda|shelf2|box1|20
cupboarda|shelf3|can1|30
我正在尝试将其转换为 json,例如:-
{
"id": "cupboarda",
"shelf": {
"shelf1": {
"package": {
"can1": {
"price": "10"
},
"box1": {
"price": "20"
}
}
},
"shelf2": {
"package": {
"can1": {
"price": "10"
},
"box1": {
"price": "20"
}
}
},
"shelf3": {
"package": {
"can1": {
"price": "30"
}
}
}
}
}
我认为我在链接中的示例上走在了正确的轨道上,但我对嵌套它的方式有点卡住了。
这是我尝试将所有内容放入一种块中的一种方法,因此我可以找出一些逻辑,将字段提取到嵌套 JSON 或嵌套哈希中,然后我可以将其格式化为 json 或其他东西否则。
require 'csv'
csv_data = CSV.read 'data.csv', :col_sep => "|"
headers = csv_data.shift.map {|i| i.to_s }
string_data = csv_data.map {|row| row.map {|cell| cell.to_s } }
array_of_hashes = string_data.map {|row| Hash[*headers.zip(row).flatten] }
puts "Array"
p array_of_hashes
让我束手无策的是试图弄清楚如何使用 id 中的值并开始分割和嵌套数据。 刚从 Ruby 开始,所以逻辑部分是我的砖墙,上面的代码是我在其他地方找到的,我认为它给了我想要的东西,但可能不是最好的方法。
更新>
我仍然试图围绕这个逻辑来思考,但到目前为止我已经走了多远:-
require 'csv'
require 'json'
csv_data = CSV.read 'inv.csv', :col_sep => "|"
headers = csv_data.shift.map {|i| i.to_s }
string_data = csv_data.map {|row| row.map {|cell| cell.to_s } }
array_of_hashes = string_data.map {|row| Hash[*headers.zip(row).flatten] }
summary = {}
array_of_hashes.each do |rec|
ida, shelfa, packagea, pricea = rec.values_at('id','shelf','package','price')
((summary[ida] ||= {})[shelfa] ||= {})[packagea] ||= 0
summary[ida][shelfa][packagea] = pricea
end
puts summary.to_json
puts summary
如果我将数据放入名为 inv.csv 的文件中,会产生接近我想要的结果。
我得到这个输出
{"cupboarda":{"shelf1":{"can1":"10","box1":"20"},"shelf2":{"can1":"10","box1":"20"},"shelf3":{"can1":"30"}}}
{"cupboarda"=>{"shelf1"=>{"can1"=>"10", "box1"=>"20"}, "shelf2"=>{"can1"=>"10", "box1"=>"20"}, "shelf3"=>{"can1"=>"30"}}}
我只需要弄清楚我可以让谁紧凑,例如:-
{"cupboard":"cupboarda","shelf":{"shelf1":{"package":{"can1":{"price":"10"},"box1":{"price":"20"}}},"shelf2":{"package":{"can1":{"price":"10"},"box1":{"price":"20"}}},"shelf3":{"package":{"can1":{"price":"30"}}}}}
【问题讨论】:
-
请展示你的努力。
-
你到底尝试了什么?请发布您的实际代码。
-
首先我尝试了链接中的示例。然后我尝试这个例子把它转换成一个哈希数组
require 'csv' csv_data = CSV.read 'data.csv', :col_sep => "|" headers = csv_data.shift.map {|i| i.to_s } string_data = csv_data.map {|row| row.map {|cell| cell.to_s } } array_of_hashes = string_data.map {|row| Hash[*headers.zip(row).flatten] } puts "Array" p array_of_hashes然后我计划提取一些uniq值来执行一些搜索以产生嵌套输出cupboard = array_of_hashes.map { |h| h["cupboard"] }.uniq -
@Steve 正如您所看到的,代码在 cmets 中的可读性不是很高。可以,甚至更喜欢将您尝试过的代码放在问题本身中。您可以在您的问题上单击“编辑”并添加它,说明这是您迄今为止尝试过的。