数値引数の利用の多くの例が,次の構文で説明することができます:
a(X,T):[1]a([2],T-1)[3]
[1],[2],[3]には適当なXの式が入ると考えてください.
Xは[2]の規則に従って成長していくのでそれをX0,X1,…と書くことにしましょう.
たとえばa(**,3)というような実行をするとします.このとき次の順番で実行されることがわかります.
同様の動きを数値のない再帰で育てようとすると
3変数かかったりして実は結構大変です.「a(X,Y,Z):a(sX,YX,XZ) と育ててYZと実行する」
ような羽目になるのだと思います.なお一見似ているコードとしては
a(X,Y):Ya(sX,XYX), a(r,)
のようにして,Yの前後に付け足していくことが考えられますが,
これは見た目の類似とは裏腹に,「大で小を挟む」が実現されます.
つまり,数値と再帰の特性は
この「数値の基本構文」の利用方法としては,それ1発で解けるというときもあれば
「小で大を挟む」型のボムとして利用する(特に連打する)ことも多いです.例えば,
a(X,T):Xa(sX,T-1)X, b:a(r,10)b, b
とかでしょうか.繰り返しに放り込んだだけですね.
「育てたパターンを連打したい」ときには,再帰で育てる場合は,育てたパターンを
育ちすぎる前に適切な回数連打する必要がありますが,数値で育てた場合は
育つ途中が実行されず,育ちすぎていく心配もないので,たくさん繰り返すなどの融通は利きやすいです.
再帰でやると位置合わせや向き合わせの苦労が多い場合にお勧めでしょうか.
特に,壁の影響で「十分たくさん繰り返せばそのうち経路に乗る」というようなときは,
数値で書いた方が確実に落ち着いて位置合わせできる気がします.
「育てたパターンを連打したい」とき,稀に使える方法が,
さらに数値引数含みの関数の再利用です.例えば先ほどの
a(X,T):Xa(sX,T-1)X, b:a(r,10)b, b
という例でも,2回実行したいだけならばa(a(r,10),1)と書けばよいですね.
たくさん実行する場合,a(a(r,10),100)とかすると余分なsがついてしまいますが
これを逆に利用できる(あるいはついても問題ない)ような場合もあります.
あまり気のきいた具体例を挙げられなくて申し訳ないですが,数値でパターンを作った場合には
その再利用を選択肢の1つとして考える癖をつけておくとよいでしょう.
使える場面は結構少ないですが,その分上手く使えるとかなり嬉しい感じだったりします(笑)