研究の関係で、37MBのXMLファイルに対して、XPathでデータを取り出したいという状況が起きました。
プロトタイプ実装として、Ruby標準ライブラリのrexmlでその処理プログラムを記述したのですが、
実行時にメモリを700MB以上消費しやがります
768MBしか積んでない私のマシンでは、メモリスワップが発生しまくりで実行が極端に重いため、
別の手段を考えることにしました。
手段としては2通り思いつきます。
- メモリ使用効率の良いXMLライブラリを使う
- SAX
Simple API for XMLの略 を使う
SAXで処理を実装するのはダルイので、今回は1番の手段にしました。
採用したXMLライブラリは、libxml-rubyっていうlibxmlのRuby Bindingです。
libxmlは、C言語で実装されたXMLライブラリで、libxml-rubyは、それをRubyで呼び出せるようにしたものです。
rexmlはRubyコードのみで実装されたXMLライブラリでして、libxml-rubyより実行速度が遅いです
きっと、メモリ使用効率もlibxml-rubyの方がいいだろうと期待して、採用しました。
rexmlはRuby1.8では標準で入ってますが、libxml-rubyは自分でインストールする必要があります。
インストールは、RubyGemsを使うと楽です。
私のCentOS 5環境下では以下の手順でインストールできました。
$ yum install libxml2-devel $ yum install ruby-devel $ gem install libxml-ruby
libxml-rubyを使って実装しなおしてみたところ、実行時の消費メモリは最大でも360MB程度になりました。
これなら、私のマシンで普通に実行できます。
XMLファイルサイズ、ライブラリ、メモリ消費量
DOM操作にしろXPathにしろ、DOM Treeを作るのに一番メモリを消費すると
思うんですが、実際、どの程度メモリを消費するのか気になったので、適当にググって見つけた
リンクを貼っときます。