为什么重复的JSON解析消耗越来越多的内存?

vre*_*sys 11 ruby memory json memory-leaks

似乎在Ruby中一遍又一遍地解析相同的JSON文件会占用越来越多的内存.考虑下面的代码和输出:

  1. 为什么在第一次迭代后没有释放内存?
  2. 解析后,为什么116MB JSON文件会占用1.5Gb的RAM?考虑到文本文件被转换为哈希值,这是令人惊讶的.我在这里错过了什么?

码:

require 'json'

def memused
  `ps ax -o pid,rss | grep -E "^[[:space:]]*#{$$}"`.strip.split.map(&:to_i)[1]/1024
end

text = IO.read('../data-grouped/2012-posts.json')
puts "before parsing: #{memused}MB"
iter = 1
while true
  items = JSON.parse(text)
  GC.start
  puts "#{iter}: #{memused}MB"
  iter += 1
end
Run Code Online (Sandbox Code Playgroud)

输出:

before parsing: 116MB
1: 1840MB
2: 2995MB
3: 2341MB
4: 3017MB
5: 2539MB
6: 3019MB
Run Code Online (Sandbox Code Playgroud)

Thi*_*win 4

当 Ruby 解析 JSON 文件时,它会创建许多中间对象来实现目标。这些对象保留在内存中,直到 GC 开始工作。

如果JSON文件结构复杂,数组和内部对象较多,数量也会增长得很快。

您是否尝试调用“GC.start”来建议 Ruby 清理未使用的内存?如果内存量显着减少,则表明只是用于解析数据的中间对象,否则,您的数据结构很复杂,或者有一些库无法释放您的数据。

对于大型 JSON 处理,我使用 yajl-ruby ( https://github.com/brianmario/yajl-ruby )。它是用 C 语言实现的,占用空间小。