ripperの使い方
どう書く?.orgのお題を解くときにripperの使い方を少し調べたのでメモ
ripperはRubyプログラムの解析を行うためのライブラリです。現在のところ字句解析のみがサポートされています(と思います...)。
Ruby 1.9.0に標準添付されていますが、驚くほどドキュメントが少ないです。
ripperには3つの使い方があります
今回はfilterを使ってみました。
filerの使い方はサンプルプログラムのstrip-comment.rbがわかりやすいです。
# $Id: strip-comment.rb 11708 2007-02-12 23:01:19Z shyouhei $ require 'ripper/filter' class CommentStripper < Ripper::Filter def CommentStripper.strip(src) new(src).parse(nil) end def on_default(event, token, data) print token end def on_comment(token, data) puts end end CommentStripper.strip(ARGF)
こんな感じで、Ripper::Filterを継承したクラスを作って、特別扱いしたいイベントの処理(on_commentとか)のメソッドを定義して、その他のイベントはon_defaultで処理するという感じでプログラムが作れます。on_defaultは次のような引数をとります。
- event イベントの名前
- token 読み込んだトークン
- data 複雑なので後述
個々のイベント処理ではeventが無く、tokenとdataをとります。
では、on_commentのほかのイベントの名前はというと・・・、残念ながらまとまったドキュメントは見つからなかったのですが、こんな感じのプログラムで調べられるんじゃないかなと思います。
require 'ripper' class RipperTest<Ripper::Filter def on_default(event, token, data) print "#{token.inspect}\t #{event} \n" end end print RipperTest.new(ARGF).parse(nil)
今まで調べたイベントとしては、こんな感じです。ほかにもものすごくたくさんあります。
このように定義したRipper:: Filterを継承したクラスは次のようにして使います。例えば、このようなクラスをFooとします。
インスタンスを作ります
r = Foo.new(RubyソースコードのIOオブジェクト)
インスタンスが作成できたら、解析を行います
r.parse(初期値)
parseで解析が始まると、各イベントメソッド(on_defaultとかon_comment)のdata引数(説明を後回しにしたもの)に初期値が渡ってきます。イベントメソッドでdataを書き換えることが出来ます。最終的なdataの値がparseの値になります。
例えば、
r.parse('')
としておいて、各イベントメソッドで、
data << token