before lisps just part of the past #2 ~ japanese symbols ~
TRANSCRIPT
Before Lisps
Just Part of the Past
~ #2 Japanese symbols ~
注意!
• 今日の話はすべてのCommon Lisp処理系で動くというわけではありません!
• 以下の処理系では動きます – SBCL – CMUCL – CLISP
• 是非他の処理系で試して報告してください
ある日のこと
!?
日本語のシンボルは使えるらしい
そういえば…
もしmacro
(defmacro もし(test then &optional else) `(if ,test ,then ,else)) (defun 偶数? (n) (evenp n)) * (もし (偶数? 10) ‘偶数! ‘奇数!) => 偶数!
もしかして
リーダマクロも…?
「 macro character (set-macro-character #\「 (lambda (strm c) (declare (ignore c)) (funcall (get-macro-character #\") strm #\」))) (set-macro-character #\」 (get-macro-character #\))) * 「こんにちは」 => “こんにちは”
・回dispatch macro character
(make-dispatch-macro-character #\・ t) (set-dispatch-macro-character #\・ #\回 (lambda (strm c n) (declare (ignore c)) (let ((form (read strm t nil t)) (counter (gensym))) `(dotimes (,counter ,n) ,form))))
・回dispatch macro character
* (let (lst) ・3回(push ‘にゃん lst) lst) => (にゃん にゃん にゃん)
助詞を導入 (set-macro-character #\と (lambda (strm c) (declare (ignore strm)) (intern (string c)))) (set-macro-character #\を (lambda (strm c) (declare (ignore strm)) (intern (string c)))) NON-TERMINATINGPをNIL(デフォルト)にすることで、字句解析をReaderに任せられる
・。dispatch macro character
(set-macro-character #\・ (lambda (strm c) (declare (ignore c)) (destructuring-bind (op . args) (reverse (read-delimited-list #\。 strm t)) `(,op ,@(mapcan (lambda (x) `(',(car x) ,(cadr x))) (group args 2)))))) * (read-from-string "・1と2を足す。") => (足す ‘を 2 ‘と 1)
・。dispatch macro character
(defun 足す (&key ((と a)) ((を b))) (+ a b)) * ・1と2を足す。 => 3 * (let ((a 10) (b 20)) ・aをbと足す。) => 30
楽なのはここまで
• 2文字以上からなる助詞はこの方法が使えないので、字句解析を自前でやる必要がある。CLでやる旨味の半分は字句解析をREADERに任せられることであり、その利点は失われる。
• 字句解析を自分で書いても、変換先がS式なのでほかの言語で実装するよりは楽なはず
最後に
このスライドは日本語プログラミングを推奨・応援するものではありません! ソースはASCII文字で書きましょう!