35. デバッグについて


長めの命令や関数を定義して実行した際に,エラーメッセージが出力されたり期待通りの動作をしないということは少なくない.そのような場合,関数ならばどこに誤りがあるのかを探して見つけて修正しなければならなくなる.この誤りを修正する一連の作業のことをデバッグという.

cat() や print() を使うデバッグ

古典的でかつよくやられている方法に,関数の途中で cat() や print() を使って,バグの原因かもしれない怪しい変数の値を関数の途中で評価途中で表示させる方法がある.この方法は手軽で確実にデバッグできるが,試行錯誤の手間がかかりすぎる欠点がある.

例えば関数 myfunc() を定義したときに,変数 x ,y ,s の途中の値が知りたい場合は以下のようにする.

 
 myfunc <- function(z) {
   x <- rnorm(1);       y <- rnorm(1)
   cat("x =", x, "\n"); cat("y =", y, "\n")             # 現在の x と y の値を調べる
   ifelse( ((x < 0) || (y < 0)), s <- -x*y, s <- x*y )
   cat("s =", s, "\n")                                  # 現在の s の値を調べる
   return(s*z)
 } 
 myfunc(5)

x = 1.305908 
y = -0.1477835 
s = 0.1929916 
[1] 0.9649579

R に用意された関数を使うデバッグ

便利なことに R にはデバッグを支援するための関数がいくつか用意されている.詳しくはヘルプを参照されたい.

関数

機能

browser()

評価の途中で変数を調べる.(デバッグ中に入力できるコマンド

→ c:関数の実行を継続,n:関数の残りの部分を一行ずつ実行,ls():生成されたオブジェクトを全て表示,関数中の変数や式:現時点の値を表示,where:現在のスタックを表示,return():関数評価に戻る,Q:終了)

debug()

デバッグモードに入る.デバッグ中に入力できるコマンドは browser() で使用できるコマンドと同じ.デバッグモードを抜ける場合は関数 undebug() を実行する.

trace()

関数の呼び出しを追跡する.追跡モードを止める場合は関数 untrace() を用いる.

traceback()

呼び出されたスタックを表示する.

debugger()

R 用デバッガを起動する.

try()

関数の途中でエラーが起きても,関数の残りを実行する.

stopifnot()

引数に与えた条件が満たされないときにプログラムをストップする.

system.time()

プログラムの実行時間を計る.

Sys.sleep()

プログラムの実行を指定秒数中断する.

以下に関数 browser() の使用例を挙げる.

 
 myfunc <- function(z) {
   x <- rnorm(1);   y <- rnorm(1)
   ifelse( ((x < 0) || (y < 0)), s <- -x*y, s <- x*y )
   browser()
   return(s*z)
 } 
 myfunc(5)

Called from: myfunc(5)
Browse[1]> ls()          # 生成されたオブジェクトを全て表示
[1] "s" "x" "y" "z"
Browse[1]> x             # x の値を表示
[1] -0.3039924
Browse[1]> c             # 関数の実行を継続
[1] 0.6327254