我从1,000个批次的服务器中获取大约20,000个数据集.每个数据集都是JSON对象.坚持这使得大约350 MB的未压缩明文.
我的内存限制为1GB.因此,我将每个1,000个JSON对象作为数组写入附加模式的原始JSON文件中.
结果是一个包含20个JSON数组的文件,需要进行聚合.无论如何我需要触摸它们,因为我想添加元数据.通常Ruby Yajl Parser可以这样做:
raw_file = File.new(path_to_raw_file, 'r')
json_file = File.new(path_to_json_file, 'w')
datasets = []
parser = Yajl::Parser.new
parser.on_parse_complete = Proc.new { |o| datasets += o }
parser.parse(datasets)
hash = { date: Time.now, datasets: datasets }
Yajl::Encoder.encode(hash, json_file)
Run Code Online (Sandbox Code Playgroud)
这个解决方案的问题在哪里?问题是仍然将整个JSON解析为内存,我必须避免.
基本上我需要的是一个解决方案,它从IO对象解析JSON并同时将它们编码到另一个IO对象.
我假设Yajl提供了这个,但我没有找到方法,它的API也没有给出任何提示,所以我猜不是.是否有支持此功能的JSON Parser库?还有其他解决方案吗?
我能想到的唯一解决方案就是使用这些IO.seek功能.写的所有数据集阵列此起彼伏[...][...][...],每个数组后,我找回到开始并覆盖][有,,有效手动连接的阵列.
我有一个包含JSON哈希的大文件(> 50Mb).就像是:
{
"obj1": {
"key1": "val1",
"key2": "val2"
},
"obj2": {
"key1": "val1",
"key2": "val2"
}
...
}
Run Code Online (Sandbox Code Playgroud)
我想解析散列中的每个项目,而不是解析整个文件并说出前十个元素.我实际上并不关心关键,即obj1.
如果我将上面的内容转换为:
{
"key1": "val1",
"key2": "val2"
}
"obj2": {
"key1": "val1",
"key2": "val2"
}
Run Code Online (Sandbox Code Playgroud)
我可以使用Yajl流轻松实现我想要的东西:
io = File.open(path_to_file)
count = 10
Yajl::Parser.parse(io) do |obj|
puts "Parsed: #{obj}"
count -= 1
break if count == 0
end
io.close
Run Code Online (Sandbox Code Playgroud)
有没有办法在不必更改文件的情况下执行此操作?也许在Yajl中有某种回调?