[Ruby] メソッド単位でのトレース
プログラムの解析、デバックに使える、メソッド単位でのトレースモジュールを作ってみました。
Ruby のメソッドは最後に評価した式が戻り値となります。したっがて戻り値をトレース(表示)するのには一工夫が必要で悩んでいましたが、ruby-list ML で良い方法を教えてもらいました 。 ありがとうございます!
Ruby では ブロック付きメソッド呼び出し が行えるので メソッドの引数と戻り値を表示するメソッドが簡単に書けてしまいます。
- トレースモジュール
module MethodTrace def m_trace(*args) a = args.inspect a.sub!(/^\[/, "(").sub!(/\]$/,")") $stderr.print "#T ", indent(+1), caller_name(), a, "\n" ret = yield $stderr.print "#T ", indent(-1), caller_name(), " = ", ret.inspect, "\n" ret end private def caller_name caller(2).first.scan(/`(.*)'/).to_s end def indent(d) $_inspect_print_level = 0 unless $_inspect_print_level $_inspect_print_level -= 1 if (d < 0) level = " " * $_inspect_print_level $_inspect_print_level += 1 if (d > 0) return level end end include MethodTrace
- MethodTrace を使ったコード
require 'method_trace' def max2(a, b) m_trace(a, b) { if (a > b) a else b end } end def max3(a, b, c) m_trace(a, b, c) { max2(a, max2(b, c)) } end max3(1,2,3)
- 実行結果
#T max3(1, 2, 3) #T max2(2, 3) #T max2 = 3 #T max2(1, 3) #T max2 = 3 #T max3 = 3