8

Amazon EC2 マイクロ インスタンスで 12 時間ごとに cron ジョブを実行しています。118MB のファイルをダウンロードし、json ライブラリを使用して解析します。もちろん、これによりインスタンスのメモリが不足します。私のインスタンスには 416 MB の空きメモリがありますが、スクリプトを実行すると 6 MB に低下し、OS によって強制終了されます。

ここで私のオプションは何ですか?これを Ruby 経由で効率的に解析することは可能ですか、それとも C のような低レベルのものに落とし込む必要がありますか? より高性能な amazon インスタンスを入手できますが、Ruby 経由でこれを行うことが可能かどうかを本当に知りたいです。

更新: yajl を見てきました。解析時にjsonオブジェクトを提供できますが、問題は、JSONファイルにルートオブジェクトが1つしか含まれていない場合、すべてのファイルを解析する必要があることです. 私のJSONは次のようになります。

--Root
   -Obj 1
   -Obj 2
   -Obj 3

だから私がするなら:

parser.parse(file) do |hash|
  #do something here
end

ルート オブジェクトは 1 つしかないため、JSON 全体を解析します。Obj 1/2/3 がルートの場合、1 つずつ提供されるので機能しますが、私の JSON はそうではなく、解析して 500 MB のメモリを消費します...

更新 # 2: これは、118 MB の大きなファイル (7 MB) の縮小版です。

なくなった

解析可能です。ファイルから数バイトを削除しただけでなく、全体として見ることができます。私が探している配列はこれです

events = json['resultsPage']['results']['event']

ありがとう

4

2 に答える 2

6

YAJLはストリーミング パーサーを実装します。これを使用してオンザフライで JSON を読み取ることができるため、コンテンツが入ってきたらそれを操作し、処理が終わったらそれら (およびそれらから生成されたデータ構造) を破棄できます。あなたがそれについて賢いなら、これはあなたをあなたのメモリ制限の下に保つでしょう.

編集: データでは、オブジェクト全体を解析するのではなく、JSON オブジェクトの一部を一度に引き出すことに本当に関心があります。これはかなりトリッキーで、独自のパーサーを実装する必要があります。その基本は、次のことです。

  1. イベント配列にステップインする
  2. 配列内の各イベントについて、イベントを解析します
  3. 解析されたイベントをコールバック関数に渡します
  4. 解析されたイベントとソース入力を破棄して、次のイベントのためにメモリを解放します。

ここでは複数のオブジェクトではなく 1 つのオブジェクトを扱っているため、これは yajl では機能しません。yajl で動作させるには、JSON を手動で解析してイベント オブジェクトの境界を検出し、各イベント オブジェクト チャンクを JSON パーサーに渡して逆シリアル化する必要があります。Ragel のようなものを使用すると、このプロセスを簡素化できます。

もちろん、AWS インスタンスをアップグレードするだけの方が簡単です。

于 2012-12-21T16:43:40.617 に答える
0

yajiのようなものは、json をストリームとして解析できます

于 2012-12-21T16:43:51.037 に答える