EmacsでLispの覚え直し(その5)

前回最後に作った関数は、括弧の閉じる位置を間違えて作ってしまいました。
if関数のelse側で、0を返すように作ったつもりですが、then側に0が入ってしまっています。
(0を返す意味がないのは置いておきます)

間違えやすいのはLispを一行で書いているからでしょう。

(defun count (n) (if (> n 0) (progn (princ n) (count (- n 1)) 0)))

このプログラムをC言語風に改行と空白を入れて書き換えてみると、

(defun count (n)
  (if (> n 0)
    (progn
      (princ n)
      (count (- n 1))
      0 
    )
  )
)

対応する括弧の位置が同一桁にしたので、すごくわかりやすくなりました。
then側に0を入れていることは一目瞭然ですね。

else側に0を入れたかったので、下のようなプログラムを想定してました。

(defun count (n)
  (if (> n 0)
    (progn
      (princ n)
      (count (- n 1))
    )
    0 
  )
)

どのようなスタイルが、Lispらしい書き方になるのかは、知りませんが、
いろいろ試して一番自分にあったものを編み出してみたいと思います。

まずは、一行スタイル

(defun count (n) (if (> n 0) (progn (princ n) (count (- n 1))) 0 ))

論外ですね。ワンライナーはコマンドラインだけにしたいものです。

例えば、リストの2番めの値を取得する処理を書く時、Lispなら、

(car (cdr (list 10 20 30)))

これぐらいならワンライナーでも良いと思ってしまいますが、
これをコマンドライン風に書くと、

list 10 20 30 | cdr | car

もっとスッキリかけます。コマンドラインだからこそ、ワンライナーなのであって、
括弧を多用するLispは、ワンライナーを想定した言語設計になっていないと思いますので、やめておいた方がいいと思いました。

C言語タイプ

(defun count (n)
  (if (> n 0)
    (progn
      (princ n)
      (count (- n 1))
    )
    0 
  )
)

この書き方は、他の言語で慣れてるので、一番読みやすいのですが、
Lispとして読みやすいのかは、まだ分からないです。

括弧だけの行を作らないタイプ

(defun count (n)
  (if (> n 0)
    (progn
      (princ n)
      (count (- n 1)))
    0))

Pythonのようなドキュメントチックな書き方ですが、今は読みにくくても、訓練次第でソース理解が早くなりそうです。

括弧は外枠タイプ

(defun count (n)
 (   if (> n 0)
 (       progn
 (            princ n        )
 (            count (- n 1)  )
 )       0                   ))

枠にしか見えなくなった括弧は、数えるのが面倒です。左括弧だと思ったら右括弧だし、右上に囲いがないから、バグが侵入してきそうなプログラムです。
この書き方もやめた方が良いと思いました。

コメント

タイトルとURLをコピーしました