2010/05/19

t, nil, '(), #t, #f

メモっておきたかったので、勝手にまとめました。「誰でも編集可」です。

私の日本語がカオスですいませんでした・・・。

「scheme も Common Lisp みたいに、nil が偽で空リストも偽で空リストが nil 、だと良いのになー。」「(car nil) や (car '()) が nil なのも良いなー。」と思ったのでした。なんで Scheme はそうじゃないんだろう?というのが切欠です。




Chaton の方からも転載・・・。
shiro
#
@valvallow @finalfusion 括弧のざわめきに混じって俺を呼ぶ声が聞こえた、ような気がした。
#
nil問題はいくつかの要素が絡んでいるので、分けて考えると良いかと思う。
#
とりあえず返しておける値があると便利、という話と、それがリストのゼロ元である()であると便利、という話。
#
とりあえず返しておける値、というのは、例えばwhenの条件不成立時とか、findで値が見つからなかった時とか、そういう何かの不成立を示すユニバーサルな値ってこと。
#
値そのものは何でも良いんだけど、条件判断と組み合わせた時に偽と判断されるようになってると色々便利。
#
ちょっと一休み
2010/05/19 02:23:04 PDTshiro
#
一方で、主要なデータ型のゼロ元が偽になるようになっていると便利、ということがある。再帰/繰り返ししていってゼロ元に出会ったら終わり、という処理が短く書けることが多いから。
#
リストが主要なデータ型であれば、空リストが偽であると便利。
#
整数が主要なデータ型であれば、0が偽であると便利 (C言語とかね)。
#
中には、リストのゼロ元も整数のゼロ元も文字列のゼロ元も偽にしちゃおうって言語もある (Perlとか)。
#
ただ、この二つの要素、どちらもトレードオフがある。
#
不成立/不存在を示す値=偽値、という設計だと、「偽値が見つかった」という答えを返すのがちょっと困る。gethashでnilが返って来た時、値は存在しなかったのか、それともnilという値だったのか。
#
CLでは多値を使ったりしてこの問題を回避するけど、アドホックな感じは否めない。厳密にやるなら、「どんな値とも一致しない値」を使って不存在を示すしかなくて、そうすると例えばHaskellのMaybeみたいに値を一段ラップしてやることになる。
#
ゼロ元=偽、という設計についても、そのデータ型にとっては便利になるんだけど、他のデータ型にとっては便利にならないっていう非一貫性がある。CLで()が偽で便利なのは、リストばっかり使うからそう思ってるだけ。Cで書いてて0が偽で便利なのは、整数のドメインで作業することが多いから (あと、不存在を示すヌルポインタってものもあるけど)。
#
つまり、「便利」という時には、「その機能が便利になるようなコードの書き方をしているから便利なのだ」ということになってる可能性がある。
2010/05/19 02:37:09 PDTshiro
#
Schemeは前者 (不存在を示す値) については不徹底で、findで#fが返ってくる問題とかあるんだけど、後者についてはいろんなデータ型に対して中立ってことなんじゃないかと思う。
#
結局、()と#fが区別されたらそれに依存したコードを書けて、それもまた「便利」ではあるので、どういうモデルで世界を見てるかってことなんだよね。
#
あと、シンボルのnilとtを特別扱いすることに対しては私は多いに不満。プログラマから使える単語を取り上げる言語は嫌い。
2010/05/19 02:42:54 PDTvalvallow@twitter
#
すごくよくわかりました!ありがとうございました m(_ _)m
2010/05/19 02:49:49 PDTshiro
#
CLで書いてる時は確かに()=nil=偽にばりばり依存したコードを書いてるけど。たまに「シンボルかリストかで分岐したい」なんてコードを書きそうになってnilのせいできーってなることはある。
2010/05/19 03:42:36 PDT齊藤
#
そういや R6RS が出来る前に未定義値は「未定義であることを表す (比較可能な) オブジェクト」にしようみたいな話があったと思うんですが、結局は「何も期待するな」になったのは、やっぱ Scheme 的にそういう依存は好ましくないってことなんでしょうか。
2010/05/19 03:43:38 PDTshiro
#
ああ、そんな議論がありましたね。
#
私の印象では、依存が好ましくないというより、未定義値の使いどころ/位置づけがうまく決まらなかったからじゃないかなあという気がしています。「未定義値」という値として使えるってことになると、それを普通に引数に渡したり戻り値として返したり、とやることになるわけですが、それが出来て嬉しいの/何に使えるの? ってことです。
#
「使っちゃいけない値/当てに出来ない値」を示す値、というのは矛盾していて、値として存在してしまったら使えちゃうわけですから。
2010/05/19 03:51:59 PDT齊藤
#
意味が無いところは意味が無いままな方が自然ってことですね。

shiro さんありがとうございました。


そういえば、clojure は?



On LispプログラミングGauche

0 件のコメント:

コメントを投稿