For Development HEAD DRAFTSearch (procedure/syntax/module):

3.4 デバッグ

Gaucheにはまだデバッグをサポートする機能があまり実装されていません。 デバッギングのインタフェースに関して良いアイディアがあればお寄せください。

今のところ、作者は必要な時は古典的な「プリントスタブ」方式を使っています。 Gaucheのリーダには、中間の結果を出力するために、 #?で始まるいくつかの構文が用意されています。

構文#?=exprは、exprを評価する前にまずその式自体を 表示し、評価後にその結果(複数の場合もあります)を表示します。

gosh> #?=(+ 2 3)
#?="(stdin)":1:(+ 2 3)
#?-    5
5
gosh> #?=(begin (print "foo") (values 'a 'b 'c))
#?="(stdin)":2:(begin (print "foo") (values 'a 'b 'c))
foo
#?-    a
#?+    b
#?+    c
a
b
c

註: デバッグスタブが原始スレッド(gauche.threads - スレッド参照)以外のスレッドで評価された場合、 スタブの出力には、どのスレッドから出力されたかを示す番号がつけられます。 次の例では、#<thread ...>およびプロンプトが原始スレッドのREPLの 出力ですが、続く#?=[1]...#?-[1]...make-threadにより作られたスレッドからのデバッグ出力です。 この番号はデバッグ時にスレッドを区別するためだけのもので、スレッド毎に異なりますが、 それ以外の意味はありません。

gosh> (use gauche.threads)
gosh> (thread-start! (make-thread (^[] #?=(+ 2 3))))
#<thread #f (1) runnable 0xf51400>
gosh> #?=[1]"(standard input)":1:(+ 2 3)
#?-[1]    5

構文#?,(proc arg …)は特に手続き呼び出しのための ものです。procを呼ぶ直前に引数の値を表示し、procから返ってきたら 戻り値(複数の場合もあります)を表示します。

gosh> (define (fact n)
        (if (zero? n)
            1
            (* n #?,(fact (- n 1)))))
fact
#?,"(standard input)":4:calling `fact' with args:
#?,> 4
#?,"(standard input)":4:calling `fact' with args:
#?,> 3
#?,"(standard input)":4:calling `fact' with args:
#?,> 2
#?,"(standard input)":4:calling `fact' with args:
#?,> 1
#?,"(standard input)":4:calling `fact' with args:
#?,> 0
#?-    1
#?-    1
#?-    2
#?-    6
#?-    24
120

内部的には、構文#?=x#?,xはそれぞれ単に (debug-print x)および(debuf-funcall x)と読まれ、 実際の表示についてはマクロdebug-printdebug-funcallが 処理します。詳しくはデバッグ補助を参照してください。

特別な構文を用意した理由は、(1)目的の式にデバッグスタブを付加するのに、 式全体を余分な括弧でくくらなくて良いのですぐできる (2)デバッグスタブをエディタで探したり取り除いたりするのが極めて簡単、というものです。

単純なデバッグスタブではしばしば大量にデバッグ出力が出てしまうので、 特定の条件に合致した時のみ出力を見たいことがあるかもしれません。 リーダー構文#??=test expr#??,test procedure-callは、 testが真に評価される時だけそれぞれ #??=exprおよび#?,procedure-callのように 動作します。

(define (fib n)
  (if (< n 2)
    1
    #??,(= n 5) (+ (fib (- n 1)) (fib (- n 2)))))

gosh> (fib 7)
#?,calling `+' with args:
#?,> 5
#?,> 3
#?-    8
#?,calling `+' with args:
#?,> 5
#?,> 3
#?-    8
21

内部的には、#??=test expr#??,test procedure-callはそれぞれマクロ呼び出し (debug-print-conditionally test expr)(debug-funcallt-conditionally test procedure-call)に 展開されます。



For Development HEAD DRAFTSearch (procedure/syntax/module):
DRAFT