トップページ⇒tech
1001コメント385KB

LISP Scheme

レス数が1000を超えています。これ以上書き込みはできません。
0001デフォルトの名無しさんNGNG
'(hello world)
0002デフォルトの名無しさんNGNG
ちょっと質問なんですが、
(lambda (init)
(let loop ((var init))
...(if (...) x)
... (loop (- var 1))))
こういうループをxの時点で中断したいんだけど、何か良い手段はありますか?
00032NGNG
書き忘れましたが言語はSchemeです。
0004デフォルトの名無しさんNGNG
山本和彦氏の「リスト遊び」を読んで、Lispに興味を持ったんだけど、
次に読むべき本を教えてください。
本屋に逝って探してみたけど、Lisp系の本って少ないねー。
0005デフォルトの名無しさんNGNG
>>2
(lambda (init)
(let loop ((var init))
(if (...)
x
(loop (- var 1)))))
(display "上のようにすると(...)が#tだとループを抜けて
xが返されるけど。")
(newline)
0006デフォルトの名無しさんNGNG
>>4
今だと図書館とかの方が揃うと思います。大学や専門の購買とか。
ちょっと前、〜(なんとか)LISP言語 第3版 (上・下2冊 緑色の表紙)
っての借りて読んだけど、CommonLispも含めてかなり詳しく載っていました。
下巻(応用)は難しくて良く分かんなかったけど(汗
0007デフォルトの名無しさんNGNG
>>4
Schemeでよければ、
「プログラミング言語の構造と解釈 第2版」は?
00082NGNG
>>5
なるほど。loopをifスコープ(?)の中で書いても良かったんですね。
有難うございます。
SchemeにはC言語でいうbreak/continueとかが無いみたいなんで困ってました。
(継続使えとか言われそうですが)
00092NGNG
;継続を使ったbreak/continue
(define for (lambda (start end body)
  (call/cc (lambda (break)
    (letrec
     (
      (loop
       (lambda (i)
        (if (< i end)
         (begin
          (call/cc
           (lambda (continue)
            (body i break continue)))
          (loop (+ 1 i))))))
     )
     (loop start))))))
00102NGNG
;>>9の使い方
(for 0 10
 ;body
 (lambda (i break continue)
  (cond
   ((= i 7) (break))
   ((odd? i) (printf "i=%d o" i))
   (else (printf "i=%d e" i))
  )
  (if (= i 3)
   (continue))
  (newline)))
00112NGNG
ってのが見つかったんですが、なんか難しいですね。
(まだインデントの付け方もよくわからない・・)
0012デフォルトの名無しさんNGNG
lisp 文法的に valid なアスキーアート気盆
0013>12NGNG
まずおまえがやってみせろ
0014>4NGNG
Lisp入門 中西正和 近代科学社 ISBN4-7649-0107-2
昔、古本屋で300円だったんで買ったんだけど。
あんまり良い本じゃないかも
Lispプログラミング 中山隆 杉山武司 オーム社 ISBN4-274-07377-7
これも古本屋で450円だったんで買ったんだけど。
あんまり良い本じゃない
どっちもCommonLisp以前の時代の本みたい。

大きい図書館いった方が早いかもね。

それと、Schemeならインターネットで日本語の資料結構揃いますよ。R
0015>4NGNG
プログラミング言語Scheme
http://www.sci.toyama-u.ac.jp/~iwao/Scheme/scheme.html
こっから色々収集できます。
001615NGNG
LISPの日本語のポータルサイトってあります?>>15みたいな所
Schemeは(比較的)良く見つかるんだけど
0017デフォルトの名無しさんNGNG
ポータルサイトじゃないけど
Lisper への道
http://www.geocities.co.jp/SiliconValley-Oakland/1680/rakup.html
0018デフォルトの名無しさんNGNG
LISPってインデントってどういう風にするものなんでしょう
いまいち読みやすくなりません。
本とかで見かける、
(expr ()
 (let
  ((var...
   ))
  ))) ;←この最後にまとめて閉じ括弧付けるのも納得いかないし。
やっぱ中括弧'(' ')'だけだから読みづらいでしょうね。
なんとかならないもんでしょうか
0019デフォルトの名無しさんNGNG
>16
まったく同感です。情報も少なすぎです。

Windowsでも動くFreeソフトのCommonLISPはありませんか?
日本語がきちんと動く奴。

(reverse '(あ いうえ おか))→(おか いうえ あ)

と文字化けしないで、きちんと評価される奴。
チェックボックスなどのコントロールも容易に操作できる奴があるといいんですが?
どこへ行っても無さそうなので、今はXLISP-STATを使っています。
Schemeは一応パソコンに積んで有りますが、defunの使い方がLISPと違うようなので使っていません。
0020デフォルトの名無しさんNGNG
>>19
xyzzyはいかがですか?
0021デフォルトの名無しさんNGNG
>20

ありがとう。早速、試してみます。
VBのエディタにもなっているらしいので結構いいかも。
0022#fNGNG
>>18 視覚的にはかなりつらいね。
つーことで、emacsを使わないと lispは読めない体に。
M-C-f とかないと。

括弧を入れ子ごとに色変えてくれるのとかあったけど、今一つ..
0023デフォルトの名無しさんNGNG
>>19
GNU Common LISPは、元々日本人が作った処理系(らしい)なので
シンボル名に日本語が使えるような気がします。(未確認です・・)
0024デフォルトの名無しさんNGNG
今から学習するならCommonLispが乗っかってるxyzzyが良さそうですね。
MLもあるみたいだし。
http://www.jsdlab.co.jp/~kei/xyzzy/
http://www.netlaputa.ne.jp/~henmi/lisp/xyzzy/
0025デフォルトの名無しさんNGNG
>>17 と同じ人のとこ
http://www.geocities.co.jp/SiliconValley-Oakland/1680/xyzzy_lisp.html
0026デフォルトの名無しさんNGNG
>>19
SchemeのdefineはLISPのdefunとたいして変わらないと思います。
(define proc (lambda (param...) body)または
(define (proc param...) body)
(define sym body)
LISPにあるauxとかoptやらはありませんけど。
その他、LISPの(setq 〜)の代わりに(define 〜)、
破壊操作は(〜!)とか。
rplaca→set-car!
rplacd→set-cdr!
(〜p )→(〜? )
progn→begin
など
0027デフォルトの名無しさんNGNG
>>23
試したところ日本語シンボルOKだった。GCL 2.2.1。
もとになったKyoto Common LISPを作った萩谷先生の文章が
他のスレで紹介されてた。
0028デフォルトの名無しさんNGNG
>>26
setqの代わりはset!……
0029デフォルトの名無しさんNGNG
LISP/Schemeでの双方向リストの実装について質問なんですが、
(item next prev)というリンクを作ると、リストが巡回構造になって
このままだとリストがまともに表示されなくて困ってます。
こういう場合、どういう風に作るのが良いんでしょうか。
次にSchemeのソース載せます。
003029NGNG
(define-macro create-que (lambda (l)
 (list 'define (cadr l) ''(() ()))))
(define (que-createitem item next prev)
 (cons item (cons next prev)))
(define (que-front list) (car list))
(define (que-back list) (cadr list))
(define (que-setfront list link) (set-car! list link))
(define (que-setback list link) (set-car! (cdr list) link))
(define (que-next link) (if (null? link) '() (cadr link)))
(define (que-prev link) (if (null? link) '() (cddr link)))
(define (que-setnext link next) (set-car! (cdr link) next))
(define (que-setprev link prev) (set-cdr! (cdr link) prev))
003129NGNG
(define (que-push list item)
 (let
  ( (old (que-front list))
   (new (que-createitem item '() '()))
  )
  (que-setprev new old)
  (if (null? old)
   (que-setback list new)
   (que-setnext old new))
  (que-setfront list new)
  (car new)))

(define (que-pop list) ; as item
 (let ((old (que-front list)))
  (if (null? old)
   #f
   (begin
    (if (eq? old (que-back list))
     (que-setback list '()))
    (que-setfront list (que-prev old))
    (if (not (null? (que-prev old)))
     (que-setnext (que-prev old) '()))
    (car old) ;item
   ))))
003229NGNG
pushback,popbackは30の逆操作なので省略します。
で、
(create-que dlist)
=>dlist
(que-push dlist 'a)
=>a
(que-push dlist 'b)
=>b
;ここでdlistをうっかり表示させてしまうと出力の無限ループ
;になってしまう。
dlist
=>(b () a (b () a (b () a (b () a (b () a (b () a (b ....
これをなんとかしたいんです。
003329NGNG
あ、データ構造は
dlist : (front back)
link : (item (next . prev))
です。
0034SageNGNG
Schemeって「すきーむ」って読むんですか。
「しぇーめ」だと思ってた……。
http://www.stdio.h.kyoto-u.ac.jp/~hioki/gairon-enshuu/SchemeNotes/scheme.html
0035いつでもどこでも名無しさんNGNG
表示させなきゃいいんじゃ.>>29
つーか普通の処理系は表示するとき nest levelで制限してない?
003629>35NGNG
やっぱそれしかないですか・・。
自作物なのでなんの制限もかけてなかったり(汗
0037デフォルトの名無しさんNGNG
閉じ括弧の対応をいちいち調べるのが面倒なんで色々調べてみたら、
シンタックスシュガー(?)として'[' ']'を使う書き方がある様ですね。
正式名称知りませんが。

・[a]は(a)と同じ意味。
・[は(と同じ様にネストできる。'(a (b (c [d (e [f]]] => (a (b (c (d (e (f))))))
・[を置いておくと、)が閉じてない場合]の位置で強制的に[に対応するまで閉じる。
・対応しない]がある場合、閉じてない'('括弧を全て閉じる。
って解釈でいいのかな。(自身なし
003837NGNG
例えば31のque-popを[]を使う書き方に書き換えると、
(define (que-pop list) ; as item
 (let [(old (que-front list]
  (if (null? old)
   #f
   (begin
    [if [eq? old (que-back list]
     (que-setback list '()]
    [que-setfront list (que-prev old]
    [if [not (null? (que-prev old]
     (que-setnext (que-prev old) '()]
    (car old]
うーん、括弧の対応付けが判って多少は良くなったかな?
ただ、初めて見る人にとっては、「なんじゃこりゃ?」って印象でしょうね・・(汗
0039デフォルトの名無しさんNGNG
スーパー括弧 [] はコードを入力するときには使うけど、
pp するときには普通の表示が良いなあ。
004037NGNG
「スーパー括弧」
ttp://www.asahi-net.or.jp/~LI6S-YSMR/argovent/argove14.html
「超括弧」
ttp://plaza10.mbn.or.jp/~lisp/intro.htm
検索でそれぞれ一件づつ引っかかりました。
あんまりないのかな
英語だとsuper brace?(でも見つかりませんでした

>>39
ppというか、readの段階で普通の()に変換されれば問題無いかと。
0041デフォルトの名無しさんNGNG
[]挟むだけでなんかメリハリが付く感じで良いですね>38
正直()だけだと見づらい。
こういうの突き詰めてくとM言語っぽくなる?
0042デフォルトの名無しさんNGNG
age
0043デフォルトの名無しさんNGNG
>今から学習するならCommonLispが乗っかってるxyzzyが良さそうですね

さっそく、使ってみました。うーむ。これは、かなり強力なエディタですね。
日本版Emacsといった感じ。どうもありがとう>20、24
0044デフォルトの名無しさんNGNG
だれかマクロの使い方教えてちょ
0045デフォルトの名無しさんNGNG
Scheme,List
線形リストをバランス木(AVL木など)に変換する方法を考えています。
英語のホームページを片っ端から調べてみても見つかりませんでした。
お分かりになる方はよろしくお願いします。

0046デフォルトの名無しさんNGNG
なんて読むんだ>xyzzy
臭い爺?
0047デフォルトの名無しさんNGNG
>なんて読むんだ>xyzzy

妻子と読むのですといいですね。
004844NGNG
誰も乗ってくれないので色々と思考錯誤した結果
マクロってこういうことだったのね。
リスト生成→生成したリストを再評価

(define-macro マクロ定義 (lambda (l) (cons 'define-macro (cdr l]
(マクロ定義 λ (lambda (l) (cons 'lambda (cdr l]
(マクロ定義 もしもだよ (λ (l)
 (list 'if (cadr l) (caddr l) (cadddr l]

(もしもだよ (< 0 1) #t #f)
=>#t
0049>45NGNG
バランス木かどうかわかりませんが、SLIBっていうライブラリの中にあった様なきがします。
あとは、
http://www.cs.indiana.edu/scheme-repository/SRhome.html
http://www.cs.cmu.edu/afs/cs.cmu.edu/project/ai-repository/ai/lang/scheme/0.html
この辺にコードが大量にある様です。(B-Treeとか見かけました)
0050>45NGNG
あと、有名なサイトは>>15のサイトから辿れます。
0051デフォルトの名無しさんNGNG
>48
Cの#defineと同じだよ。
機能がむちゃ強力なだけ。
FORTRAN表記をLispに直せちゃうくらい強力だが…
005244>51NGNG
ですねー。
マクロの引数の解釈に手間取りましたが(汗
(car l) => もしもだよ
(cadr) =>(< 0 1)
(caddr) =>$t
(cadddr) =>$t
構文拡張した気分になれます。

if->もしもだよみたいな単純なsyntax名の置き換えなら
(マクロ定義 もしもだよ (lambda (l) (cons 'if (cdr l]
で良いみたいですが。
005344NGNG
処理系が日本語に対応してれば、
日本語Schemeなんかも無理なく作れますね(汗

(マクロ スタック生成 (λ (仮引数)
 (リスト '定義 (かあだ 仮引数) ''()]

(マクロ 積む
 (λ (仮引数)
  (リスト '更新! (かあだだ 仮引数)
   (リスト 'コンス (かあだ 仮引数) (かあだだ 仮引数]

(マクロ 捨て
 (λ (仮引数)
  (リスト '並列レット
   [リスト (リスト '捨てるモノ (かあだ 仮引数]
   (リスト 'もしもだよ (リスト 'ぬる? '捨てるモノ) 偽
    (リスト '複文
     [リスト '更新! (かあだ 仮引数) (リスト 'くだ '捨てるモノ]
     (リスト 'かあ '捨てるモノ]
;test
(表示 'スタックのテスト)(改行)
(スタック生成 a)
(表示 a)(改行)
(表示 (積む 'x a))(改行)
(表示 (積む 'y a))(改行)
(表示 (積む 'z a))(改行)
(表示 (捨て a))(改行)
(表示 (捨て a))(改行)
(表示 (捨て a))(改行)
(表示 (捨て a))(改行)
(表示 a)(改行)
0054デフォルトの名無しさんNGNG
>>52
マクロではないですが、単純なsyntax名の置き換えなら
define文でもできます。(あたりまえかな)

(define 定義します define)
(定義します もしもだよ if)
005544>54NGNG
うちの処理系ではclosureやprimtiveはdefine置き換えできますが、
ifやletみたいなsyntaxだとエラー吐いちゃうんでマクロにしてます。
Iispのfexpr型の様なlambdaがあればできそうですが。
005654>55NGNG
Linux上のguileとSTkではエラーになりません。
R5RSとかではどうなってるんだろう。
005755>56NGNG
あ、
(define もしもだよ if)
がエラーになるってのは、単に↓を評価した場合
if
=>error:Unbound symbol 'if
これがインプリメントされてないからです。
いいかげんに作ってあるので・・(環境を返す様にすれば直る)
R5RSみても良く判りませんでした(→多分マクロが返る)
「形式的シンタックス」とか、後ろの方意味不明・・(汗
0058デフォルトの名無しさんNGNG
あげ
0059デフォルトの名無しさんNGNG
かあだだってなんだよ(w
caddrか。
そういやこれ日本語にするとなにになるんだっけ?
0060デフォルトの名無しさんNGNG
頭体体
0061デフォルトの名無しさんNGNG
顔駄目体体
0062>61NGNG
三原じゅうんこ!!
0063デフォルトの名無しさんNGNG
「三番目」か?>>59
LISPはcaxxrの代わりに
first second third forth fifth sixth seventh eighth ninth tenth
がある。
じゃあ、cdxxrとかは何よ、って思うけど。
0064デフォルトの名無しさんNGNG
car かー
cdr くだー
cadr かだー
cdar くだあー
caar かあー
cddr くだだー
0065デフォルトの名無しさんNGNG
まともに印字可能なリスト表現が
(a b c d) => (a .(b .(c .(d .()))))
の様になってることから、
普通car側のネストってしないものなんでしょうか。
(((((). d). c). b). a)
こうなるんですが。見ずらい・・
0066デフォルトの名無しさんNGNG
アクセス用の関数も同時に作ってやるだろ、そういうときは。
0067デフォルトの名無しさんNGNG
Lispはきれいだとか、意味論的にクリアだとか聞いたことがありますが,
構造化されたある程度大きなプログラムを書けるのでしょうか?

僕は結構OOPについては詳しいつもりでなんですが、
OOPとLISP系(関数型)ってどっちが美しいですか?
ぼくは
LISPの美しさがよく分かりません、っていってもぱっと見の印象もあるんだけど
0068デフォルトの名無しさんNGNG
>>67
自己スレです
意味論的にクリアなのはSchemeか?
0069>66NGNG
やっぱりそういった方法でやるしかないですか。
画面出力の時だけcdrネストに直せばいいかな
0070>67NGNG
美しいかわかりませんが、
データと関数の相互変換が自然に行なえるのは良いと思います。
それと、破壊操作やprimitive以外は全てlambda式で表現できるとか。
(define-macro compound-statement :複文のマクロ定義
 (lambda (l)
  (list (cons 'lambda (cons '() (cdr l)]

(compound-statement '式1 '式2 ...)
0071>67NGNG
あと大きなプログラムについては、型付けが弱い部類の言語なので、
モジュール毎に分けたり単体テストなどをちゃんとやらないと
直ぐに破綻すると思います。(型は実行時に判定するしか無いので。)
また、ネストする括弧は人間にはかなり見ずらいので、
なんらかの対策をする必要を感じると思います。
(超括弧[]やエディタの機能を使うとか、構文の単純化など)
0072>67NGNG
幸い、マクロ機能が強力なので、工夫すればOO風の記述も
可能になると思います。
(実際、ほとんどの処理系は初めからOO拡張している様です)
0073>68NGNG
Schemeでは末尾再帰のループ展開が言語側で正式にサポートされています。
これはlispには無い様です。(lispでは普通whileなどの制御構文などを使う)
よってSchemeでの外部ループは再帰呼出しで記述するのが一般的らしいです。
また、制御構造自体は>>70の様にlambdaで置き換える事ができます。
lispにある脱出系制御文(大域goto、catch/throw/break/returnなど)は
*継続*という概念で定義できるみたいです。(反則的な気がしますが)
0074デフォルトの名無しさんNGNG
(call-with-current-continuation
0075デフォルトの名無しさんNGNG
lispって関数型っていわれるといやーん。
CLOSなんて object systemもあるんだし。
Smalltalk並みに柔軟な、自分自身に手を入れられる環境が魅力では。
と言うことで単なる schemeはあまり触ってなかったり。
仕様的に美しいのは納得するんだけどねえ。
0076デフォルトの名無しさんNGNG
オンライン上で読める文献
アルゴリズム言語Schemeに関する第五改訂報告書(R5RS)
http://www.sci.toyama-u.ac.jp/~iwao/Scheme/r5rsj/html/r5rsj_toc.html

Common Lisp the Language, 2nd Edition(英語)
http://www.cs.cmu.edu/afs/cs.cmu.edu/project/ai-repository/ai/html/cltl/cltl2.html

Structure and Interpretation of Computer Programs(SICP)(英語)
http://mitpress.mit.edu/sicp/full-text/sicp/book/book.html
007774NGNG
)
0078デフォルトの名無しさんNGNG
>>73
Common Lispでも普通はコンパイラが末尾再帰を処理してくれる。
コンパイルしないとスタックオーバーフローになってもコンパイルすればOKな事が多い。
0079デフォルトの名無しさんNGNG
call/cc>74
0080Be名無しさんNGNG
Scheme使ってる人で「計算機プログラムの構造と解釈」を読んだことある人います?
これよんで感動しました。お勧めです。
0081デフォルトの名無しさんNGNG
>>76の3番目のリンクがそれのオンラインで読めるやつだよ>>80
英語だけど。
訳本はなかなか図書館にも置いてないなあ。
0082デフォルトの名無しさんNGNG
LispやSchemeで複数行のコメント付けるにはどうしたらいいですか?
;←しかないですか?
008382NGNG
あと、C言語の
#ifdef __UNIX__
;
#else
;
#endif
の様な物は無いでしょうか。
0084デフォルトの名無しさんNGNG
>>80
というか「読んだ人が使っている」というくらい普通に読んでると思うが。
0085デフォルトの名無しさんNGNG
Scheme Requests for Implementation(SRFI)
http://srfi.schemers.org/
0086>82NGNG
例えばですが、/*〜*/を解釈する様にreadを上書きするとかはできる様です。
SLIBのtrnscrpt.scmを見ていてそう思いました。
0087>82NGNG
がんばれば#ifdef〜#endifも自分で作れるんじゃないかと思います。
0088デフォルトの名無しさんNGNG
>>83 CommonLispにはあったよ。でも忘れてるのでsage
0089デフォルトの名無しさんNGNG
Schemeで構造体とかって作れるでしょうか。

(define-struct hoge '(method1 member1 member2))
=>hoge ;構造体の定義
(define hoge1 (make-struct hoge))
=>hoge1 ;インスタンスの生成
(member-set! hoge1 member1 'member1-value)
(member-get hoge1 member1) ;メンバのアクセサ
=>member1-value
(method-call hoge1 method1 param)
とか。これぐらいならマクロで作れそうですが、classとなると・・
(define-class
 hage ;hageクラス
 (super hoge . ()) ;hogeから単一継承
 '(method1 member1 member2)) ;hageのメンバ
(define-method
 (hage method1 msg) ;method1の定義 msgは引数
 (display (member-get self member1)) ;member1の値の表示
)
(member-set! hoge1 member1 member1-value)
(method-call hage1 method1 param)
こんな感じでしょうか。やっぱり構造体とあんまし変わらないのかな。
それにしても、なんか読みにくいなあ・・
0090デフォルトの名無しさんNGNG
>89
MITの授業内容のサイトらしいけど、OOPのサンプルがある。(SICP参照)
http://www.ai.mit.edu/courses/6.001-99Spring/lectures/lec15/lec-oops-duane/lec-oops-duane.html
0091デフォルトの名無しさんNGNG
多態までのサンプル。結構短い・・。
http://www.angelfire.com/tx4/cus/shapes/scheme.html
0092デフォルトの名無しさんNGNG
初心者の質問です。
LISPって大学や研究機関、あるいは個人の趣味以外で
仕事で利用されたりしてるのでしょうか?

sawfish,emacsは除いて。
009389NGNG
ありがとうございます。 >91-92
Schemeの標準的な構文で実現できるとは思いませんでした。

でも疑問に思ったんですが、↓のletで生成されるxとyの
入れ物の継続期間が謎なんですけど・・
↓のmake-shapeはclosure(lambda以降)を返すんですよね?
こんなことして平気なんでしょうか。
(>>91のサンプル)
(define (make-shape newx newy)
 (let (
  (x newx)
  (y newy))
  (lambda (method parms)
   (cond ; accessors for x & y
   ((eq? method 'getx) x)
   ((eq? method 'gety) y)
   ((eq? method 'setx) (set! x parms))
   ((eq? method 'sety) (set! y parms)) ; move the x & y coordinates
   ((eq? method 'moveto)
     (set! x (car parms))
     (set! y (car (cdr parms))))
   ((eq? method 'rmoveto)
     (set! x (+ x (car parms)))
     (set! y (+ y (car (cdr parms))))))
   )))

(define s (make-shape 640 480))
(s 'getx '())
=>640
(s 'gety '())
=>480
0094デフォルトの名無しさんNGNG
ACLを買った人いる?いくらなんだろ?
009589>92NGNG
わたしは残念ながら聞いたこと無いです。
LispやSchemeのコード納品する様な仕事ってどんなのでしょう(汗
cgiの部品としてperl/Pythonコードとかはある様ですが。
まあScheme->Cとか、変換ツールは結構出回ってる様なので、
元がLisp/Schemeって事例はあるかもしれません。
009689NGNG
>>90のMIT風の書き方の方
(cond->caseしただけですが)
(define (make-shape newx newy)
 (let (
  (x newx)
  (y newy))
  (lambda (method parms)
   (case method ; accessors for x & y
    ((getx) x)
    ((gety) y)
    ((setx) (set! x parms))
    ((sety) (set! y parms)) ; move the x & y coordinates
    ((moveto)
     (set! x (car parms))
     (set! y (car (cdr parms))))
    ((rmoveto)
     (set! x (+ x (car parms)))
     (set! y (+ y (car (cdr parms)))))
    (else (no-method))))))
letの辺りはよく分かりませんが、これをマクロでテンプレートにしたら
結構使えそうです。
009789NGNG
反応が無くて寂しい
0098デフォルトの名無しさんNGNG
self(this)を使いたい場合
(define (make-shape newx newy)
 (let* (
  (x newx)
  (y newy)
  (self
  (lambda (method parms)
   (case method
    ((disp)
     (display*
      (self 'getx ())
      " "
      (self 'gety ())
      "\n"))
    ((self) self)
    ((getx) x)
    ((gety) y)
    ((setx) (set! x parms))
    ((sety) (set! y parms))
    ; :
    (else (no-method))))))
  self))
(define shape (make-shape 640 400))
(shape 'disp ())
640 400
0099デフォルトの名無しさんNGNG
>>94
Professional版が414,750円,Enterprise版が1,092,000円です.
ちょっと高いね.
0100>99NGNG
ショック!個人で買うには辛いわ。
でも情報サンキュー>99
0101デフォルトの名無しさんNGNG
lisp/schemeとかのインデントってどうやるのが定説なんですか?
CならK&R、BSD、GNUと色々ある様ですが・・
とりあえずわたしは下の様な感じで落ち着きました。
(↓は全角空白=半角空白2文字)
(define (func param)
 (let (
  (var1 init1)
  (var2 init2))
  (cond ;condはテスト式が複数あるので字下げする
   ((eq? var1) (set! var1 var2)) ;一文で画面に収まるならそのまま書く
   ((eq? var1) ;複数行なら下げる
    (set! var1 var2)
    (set! var1 var2))
   (else ;#t
    (set! var1 var2)
    (set! var1 var2)
    )) ;condはelseでかならず終るので括弧をまとめる
  ;←letブロックは、まだなにか付け足すかも知れないので
  ;括弧を下げる
 )) ;let
#ネタ不足です(汗
#hashテーブルでも作ろうかなあ・・
0102デフォルトの名無しさんNGNG
>>100
100おめでとうございます〜。
0103デフォルトの名無しさんNGNG
>>99
高いですね(汗
需要があんまりないからかも。(汗だく
速度とかを問題にしない限り、自作できちゃうからかな・・
0104デフォルトの名無しさんNGNG
>>96 のletの意味がようやくわかりました。
Schemeには環境リストというものが存在します。
(環境リストは(interaction-environment)などのプリミティブで参照可能)
変数や関数の

>>96 の (lambda (method parms)〜) に入った時点で、
環境リストの状態は(処理系にもよりますが)下の様になります。

`( ;↓closureの環境…(1)
 ((method . methodの実引数) (parms . parmsの実引数))
  ;↓letの環境
 ((x . ,newx) (y . ,newy)))
  ;↓グローバルな環境
 (...
 (car #<PRIMITIVE >)))

これを踏まえると、つまりmake-shapeを呼出した時に返るclosureの
環境は(1)の地点にあるので、そのままletの環境も巻き込まれると
言う事です。巻き込んだ環境はclosureへ一緒に束縛されます。

(Cで同じ事をしようとすると、子関数のスタック変数のアドレスを
保持したポインタを返す様な形になり意味が無い。
子関数のスタックフレームを持ち帰るような事なので、Cの仕様では無理。)
0105104NGNG
補足
>変数や関数の
→無視
>Cの仕様では無理
→Cでも処理系依存な方法ですがスタックアドレスを取得して、
フレームをコピーすれば可能です。
0106104NGNG
つまり継続が使えるScheme独特のコードと言うことです。
(LispだとCと同様な事が起る。)
0107104NGNG
ああ、
>(LispだとCと同様な事が起る。)
これは確認したわけでは無いので違ってたらすいません。
0108104NGNG
これがあるお陰で、Lispでは専用の構文が用意されている構造体、
クラスも、Scehmeでは限られた言語仕様の中で表現できます。
0109デフォルトの名無しさんNGNG
相互リンクしてみる
http://mentai.2ch.net/test/read.cgi?bbs=prog&key=963134110&ls=100
0110デフォルトの名無しさんNGNG
>>108
少なくともCommon Lispならできるよ。
0111104>110NGNG
なんのことですか?
letの環境の辺りの事かな?
0112104>110NGNG
一応、GUY L.STEELE JR.のCommonLISP第2版 (日本語訳)の本は
持ってるんですが、この本に書いてあります?
SchemeのR5RSだと抽象的すぎて書いてあったとしても
意味がつかめないんで・・
0113デフォルトの名無しさんNGNG
ネタが無いんでhashテーブルでも

(define (hash obj) (object->number obj))
(define (hash-iter cmp obj tbl) ; as number or #f
 (let* (
  (num (vector-length tbl))
  (value (% (hash obj) num)))
  (if (cmp (vector-ref tbl value))
   value
   (let loop ((pos (+ value 1)) (neg (- value 1)))
    (cond
     ((and (>= pos num) (< neg 0)) #f)
     ((and (< pos num) (cmp (vector-ref tbl pos))) pos)
     ((and (>= neg 0) (cmp (vector-ref tbl neg))) neg)
     (else (loop (+ pos 1) (- neg 1))))
   ))
 ))

(define (find-hash-sub obj tbl)
  (hash-iter
   (lambda (pair) (or (null? pair) (eqv? (car pair) obj))) obj tbl))
0114デフォルトの名無しさんNGNG
(define (make-hash num) (make-vector num))
(define (hash-length tbl) (vector-length tbl))

(define (add-hash-pair pair tbl)
 (let ((value (find-hash-sub (car pair) tbl)))
  (if (and (number? value) (null? (vector-ref tbl value)))
   (vector-set! tbl value pair)
   #f)
 ))

(define (add-hash obj data tbl)
 (add-hash-pair (cons obj data) tbl))

(define (find-hash obj tbl)
 (let ((value (find-hash-sub obj tbl)))
  (if (and (number? value) (not (null? (vector-ref tbl value))))
   (vector-ref tbl value) #f)
 ))
0115デフォルトの名無しさんNGNG
(define-macro prog1
 (lambda (l)
  (list 'let (list (list 'r (cadr l)))
   (cons 'begin (cddr l))
   'r)))

(define (remove-hash obj tbl)
 (let ((value (find-hash-sub obj tbl)))
  (if (and (number? value) (not (null? (vector-ref tbl value))))
   (prog1
    (vector-ref tbl value)
    (vector-set! tbl value ()))
   #f)
 ))
0116デフォルトの名無しさんNGNG
(define (rehash num tbl)
 (let (
  (v (make-hash num))
  (old (vector-length tbl)))
  (let loop ((n 0))
   (cond
    ((>= n old) v)
    ((or (null? (vector-ref tbl n))
       (add-hash-pair (vector-ref tbl n) v))
     (loop (+ n 1)))
    (else v))
  )))

(define (hash-count tbl)
 (let loop ((c 0) (n (- (vector-length tbl) 1)))
  (cond
   ((< n 0) c)
   ((null? (vector-ref tbl n)) (loop c (- n 1)))
   (else (loop (+ c 1) (- n 1))
   ))
 ))
0117デフォルトの名無しさんNGNG
;テスト
(define h (make-hash 32))
(add-hash 'add add-hash h)
(add-hash 'remove remove-hash h)
(add-hash 'find find-hash h)
(add-hash 'rehash rehash h)
(add-hash 'make-hash make-hash h)
(define h (rehash (hash-count h) h))
(display* h "\n")
0118デフォルトの名無しさんNGNG
補足
・hash表はvectorで、各要素はpairなのでvector->listすればassoc系が使えます。
・使う場合object->numberは自作してください。
0119デフォルトの名無しさんNGNG
LISPの数少ない商用利用例
http://jp.franz.com/base/success_main.html
0120118NGNG
バグ
・removeはaddの逆の順番で呼ばないと、あるパターンでうまく削除されない。
また削除できても後の要素ができなくなる可能性がある。
・rehashを行なうとaddした順番が失われるので正常に削除できくなる。
よってremoveはそのままでは使えません。
removeの時に近隣の要素のhash値を調べて適当な場所に移動させていく必要があります。
(※ここで言う「適当」とは「デタラメ」の事ではない)
0121118NGNG
修正方法1
・rehashのロジックで削除要素以外を登録し直す。
→rehash分のコストが掛かる。実装は簡単。
修正方法2
・>>120の「近隣の〜」を実装する。
→最悪、全ての要素を走査する必要がある。実装は面倒。

オープンアドレス法での要素の削除は、
あまり良い案が浮かびませんでした。
0122118NGNG
修正版remove-hash
(define (vector-ncopy dst src num)
  (let loop ((i 0))
   (cond
    ((< i num)
     (vector-set! dst i (vector-ref src i))
     (loop (+ i 1)))
    (else dst))
  ))

(define (remove-hash obj tbl)
 (let (
  (i (find-hash-sub obj tbl))
  (num (vector-length tbl)))
  (if (and (number? i) (pair? (vector-ref tbl i)))
   (prog1
    (vector-ref tbl i)
    (vector-set! tbl i ())
    (vector-ncopy tbl (rehash num tbl) num))
   #f)
 ))
0123デフォルトの名無しさんNGNG
>>119
AutoLisp(AutoCADの) や Cakewalk CAL は?
0124>123NGNG
そういやCakewalkも内蔵スクリプト入ってましたね。
持ってるけど忘れてた。
0125デフォルトの名無しさんNGNG
SchemeのObject指向のやり方については、ここに日本語で解説がありました。
(がいしゅつリンクですが。)

Schemeへの道(トップ)
ttp://www.stdio.h.kyoto-u.ac.jp/~hioki/gairon-enshuu/SchemeNotes/scheme.html
クロージャとオブジェクト
ttp://www.stdio.h.kyoto-u.ac.jp/~hioki/gairon-enshuu/SchemeNotes/closure-object.html
0126デフォルトの名無しさんNGNG
>>123
AutoLISPは固有の関数も多いし、ここでは話題になりにくいかもね。
0127デフォルトの名無しさんNGNG
age
0128デフォルトの名無しさんNGNG
call/cc (call-with-current-continuation) の使い方でも

return文
(return-scope ... (return ... result) ...end )
return-scopeはbeginと同じ様に働くが、
途中にreturnを置く事でブロックを抜けられる点で異なる。
returnを抜けた場合、resultがreturn-scopeの返り値となる。
0129デフォルトの名無しさんNGNG
;実装方法
(define-macro return-scope
 (lambda (l) `(call/cc (lambda (return) ,@(cdr l)))))
;または、
(define-macro return-scope
 (lambda (l)
   (list 'call/cc (cons 'lambda (cons (list 'return) (cdr l))))))

;;前者と後者は同じ意味。
;;`(backquote/quasiquote)の探索/展開が遅い処理系では、
;;後者の形式を使用する。
0130デフォルトの名無しさんNGNG
;;return-scopeのテスト
(define (return-test)
 (return-scope
  (define (f i) (return (display* 'return i "\n") #t))
  (display* 1 "\n")
  (display* 2 "\n")
  (if #t #t
    (return (display* 'return 3 "\n") #f))
  (f 4)
  (display* 5 "\n")
 )
 (display* 6 "\n")
 #t
)
(return-test)
1
2
return 4
6
=>#t
0131デフォルトの名無しさんNGNG
;;おまけ
(define (display* . l)
 (let loop ((x l))
  (cond
   ((pair? x)
    (display (car x))
    (loop (cdr x)))
   (else #t)
  )))
0132デフォルトの名無しさんNGNG
>>128-130の(return-scope(return))は、
恐らくcall/ccの使い方としては一番単純な物です。
0133デフォルトの名無しさんNGNG
call/ccの定義はそのまま書くと混乱するので、
上の様にマクロなどで隠蔽する事が推薦されます。
0134デフォルトの名無しさんNGNG
格調高いね、ここ。
0135デフォルトの名無しさんNGNG
厨房臭いねここ。
0136デフォルトの名無しさんNGNG
age
0137デフォルトの名無しさんNGNG
>>135-134
きみらもな
0138デフォルトの名無しさんNGNG
lispにしてもschemeにしても、この板で使ってる人どれぐらいいる?
0139デフォルトの名無しさんNGNG
確かにプログラマ板のlispスレと比べると雰囲気違うね。(w
0140デフォルトの名無しさんNGNG
call/cc (call-with-current-continuation) の使い方その2

catch - throw文
(catch 'tag ... (throw 'tag ...) ... )
(catch 'tag ... (throw-value 'tag value) ... )

catch文にはtagというラベルが存在する以外はbeginと同じように働きます。
途中にthrow文を置くことで、tagと一致するcatchブロックを抜けることができます。
catchブロックは、先に実装したreturnブロックとは異なり、
複数のcatchブロック階層を一気に抜ける事ができます。
また、throwだけの記述をした関数に対して、呼出し側でcatahを行なう事もできます。
(throw 'tag ... ) を呼出すと、最後に評価した結果がcatchから返されます。
(throw-value 'tag value) はvalueを評価した結果がcatchから返されます。
0141140NGNG
;実装方法
(define *catch-handler-stack* '())

(define (throw-value tag value)
 (let ((cont (assq tag *catch-handler-stack*))) ; as (tag . cont) or #f
  (cond
   (cont
    (set! *catch-handler-stack* (cdr (memq cont *catch-handler-stack*)))
    (apply (cdr cont) (list value)) ;; ((cdr cont) value))
   (else (error "cannot throw tag:" tag)))
 ))

(define-macro throw
 (lambda (l)
  `(throw-value ,(cadr l) (cons 'begin ,(cddr l)))))
0142140NGNG
(define-macro catch
 (lambda (l)
  (let ((throw-cont (gensym)))
   `(call/cc
    (lambda ( ,throw-cont)
     (set! *catch-handler-stack*
      (cons (cons ,(cadr l) ,throw-cont) *catch-handler-stack*))
     (throw-value ,(cadr l) ,@(cddr l))
    )))))
0143140NGNG
補足
・(gensym)は、環境に存在しないユニークなシンボルを生成する関数。
・*catch-handler-stack*の存在する場所は、
グローバル/ローカル環境どちらでも良い。
0144140NGNG
;;おまけ
(define-macro throw1
 (lambda (l)
  `(throw-value ,(cadr l) (cons 'prog1 ,(cddr l)))))
0145140NGNG
;;おまけ2
(define-macro catch1
 (lambda (l)
  (let ((throw-cont (gensym)))
   `(call/cc
    (lambda ( ,throw-cont)
     (set! *catch-handler-stack*
      (cons (cons ,(cadr l) ,throw-cont) *catch-handler-stack*))
     (throw-value ,(cadr l) (prog1 ,@(cddr l)))
    )))))
0146140NGNG
おまけのthrow1、catch1 は、最初の評価結果を返す。
0147140NGNG
>>134-139
ネタを何か書込んでください。
>>138
少なくともわたしは使ってます。
0148デフォルトの名無しさんNGNG
age
0149デフォルトの名無しさんNGNG
http://www.eval-apply.com/
0150デフォルトの名無しさんNGNG
http://www.call-with-current-continuation.org/
0151デフォルトの名無しさんNGNG
scheme :
(obj 'message param)
or (class_message obj param)
C
dispatch(obj, message, param)
or class_message(obj, param);
C++
obj->message(param);
or obj->receive(message, param);
考察
class_message形式や、
obj->messageは何を表してるのかわかりにくい。
0152デフォルトの名無しさんNGNG
>>151
まあ確かに。
矢印を使うって発想はいいんだけど。逆の意味を連想する。
せめて、obj<-message(param);
だったらいいのにね。(と、なにかの本にも書いてあった)
0153デフォルトの名無しさんNGNG
矢印は方向を表すためだけに使いたい。>152
obj <- message param
message param -> obj
とか。
0154デフォルトの名無しさんNGNG
>>153
152はそういうこと言ってるんじゃないのか?
0155デフォルトの名無しさんNGNG
>>152
'->'は元々、構造体メンバへのポインタアクセスっつう意味しかない、
低レベルな発想だからねえ・・
思わずこうしたくなるね。
obj.receive(message, param);
0156153NGNG
なるほど>154
0157デフォルトの名無しさんNGNG
>>82
#|〜|#というのがあった気が。処理系毎の独自拡張みたいだけど。

#|ここからコメント
〜
ここまでこめんと|#
0158デフォルトの名無しさんNGNG
小なり→単項演算子マイナスと紛らわしいから、
パースできないね。残念だったね。
個人的今のでいいやって感じだけど。
0159デフォルトの名無しさんNGNG
>>151
(class_message obj param) はわかるんですが (obj 'message param)
は可能なんですか?LISPでも可能ですか?
0160デフォルトの名無しさんNGNG
age
0161デフォルトの名無しさんNGNG
>>159

151じゃないけど……

・schemeなら関数呼び出しフォームの先頭要素を普通に評価してその値を関数
として使うから、可能

・common lispだとあくまで((lambda ()) foo ...)と(symbol foo...)が関数
呼び出しフォームなだけだから、ムリ

です。この辺もschemeが普通のlispと比べて美しいところのひとつ。
0162デフォルトの名無しさんNGNG
Scheme VS Lispな話も聞きたいなぁ。
どっちが優れてるかで言ったらやっぱりSchemeの圧勝?
0163さすがMITNGNG
>>7
古くてスマソ。「計算機プログラムの構造と解釈 第二版」
確かに名著。ただし非常に高度。読むときは本気で取り組まんとツライ。
0164159NGNG
>>161 サンクス、クレクレでスマソだが気が向いたら

(obj set_hoge "foo")
(obj hoge) => foo
(obj set_hoge "bar")
(obj hoge) => bar

となるような obj を簡単に定義してみてもらえないだろか。

漏れは、schemeで継続を使いこなすとカッコイイと聞いてschemeに興味
を持ったモンで、Schemeは厨房以下、emacs-lispは厨房、ほんとは
Ruby好きかも。
0165159NGNG
>>164 はちょと訂正

(obj 'set_hoge "foo")
(obj 'hoge) => foo
(obj 'set_hoge "bar")
(obj 'hoge) => bar
0166デフォルトの名無しさんNGNG
>>164
(define (make-hoge init)
 (let ((hoge init))

  ;; method set-hoge
  (define (set-hoge parms)
   (cond
    ((null? parms) #f)
    ((string? (car parms))
     (set! hoge (string->symbol (car parms))))
     hoge ;; hogeを返す
    (else
     (set! hoge (car parms))
     hoge ;; hogeを返す
    ))) ; set-hoge

  ;; message dispatcher
  (lambda (message . parms)
   (case message
    ((hoge) hoge) ; hogeを返す
    ((set_hoge) (set-hoge parms))
   ))
 ))

(define hoge_instance (make-hoge 'hoge))
(hoge_instance 'set_hoge "foo")
(hoge_instance 'hoge) ;=> foo
(hoge_instance 'set_hoge "bar")
(hoge_instance 'hoge) ;=> bar
0167166NGNG
すいません。正しくはこうでした。
 ;; method set-hoge
  (define (set-hoge parms)
   (cond
    ((null? parms) #f)
    ((string? (car parms))
     (set! hoge (string->symbol (car parms)))
     hoge ; hogeを返す
    )
    (else
     (set! hoge (car parms))
     hoge ; hogeを返す
    ))) ; set-hoge

ちなみに、
(hoge_instance 'set_hoge 'a 'b 'c)
としてたとき、各引数は
(car parms) ; =>a
(cadr parms) ; =>b
(caddr parms) ; =>c
で拾えます。(わかってるかもしれないけど一応)
0168166NGNG
(make-hoge 'hoge)
=>#<closure>
としたときに返されるのはclosureですが、
closure定義自体のコピーは行われません。(だった筈)
よって、make-hogeの中身を動的に変更する手段(メタクラス化)を
作っておくと、既に作成されたinstanceにも影響します。
インスタンス毎にコピー(というか保存)されるのは、
(make-hoge 'hoge)を実行した時のローカル環境letのhoge
だけです。
C++の一時変数の様な使い方(↓)をする場合は
defineする必要はありません。
C++
func(CHoge(hoge));
scheme
;hogeインスタkンスを作成し、
;そのインスタンスににhogeメッセージを送って
;その結果をfuncに渡す。
;hogeインスタンスは以降使われない。(後にgcで回収される)
(func ((make-hoge 'hoge) 'hoge))
0169166NGNG
過去レスにありますが、
C++のthis参照の様な事をしたい場合、
message dispatcherをthisという名前などで保存しておけば、
同様の事ができます。
>>166のmessage dispatcherの部分を下の様に書き換える。
(define this (lambda (message . params) ...))
this ; make-hogeの結果としてthisを返す。

これで、make-hogeの中でもthis経由でメッセージ式が使えます。
(this 'message params)
0170159NGNG
>>166
漏れは厨房過ぎてすぐに全ては飲み込めないが、OOP的な書き方も
ばっちりできそうだという匂いは伝わった。ありがとう!
0171デフォルトの名無しさんNGNG
>>166
(define (make-hoge init)
 (let ((hoge init))
を
(define (make-hoge hoge)
にすればletは必要ない。
lambdaパラメータも環境の一つなんで。
(make-hoge init)
これを実行した時点でhogeがinitに初期化される。

hogeインスタンスから見えるローカルフレームの環境リスト
((set-hoge . #<closure>)
(this . #<closure>)
(hoge . init))

さらにmessage dispatcher 実行時に追加される環境リスト
; 'hoge メッセージ呼出し時
((parms . ()) (message . hoge))

; 'set_hoge メッセージ呼出し時
((parms . "bar") (message . set_hoge))
0172デフォルトの名無しさんNGNG
(define (make-hoge hoge super)
と書き直して、message dispatcherの最後に下を追加すると、
(else
 (if (procedure? super)
  (apply super (cons message parms))
  #f)
単一継承モデルとかも作れる。
caseはeqv?の線形探索だからmessageが多くなると時間がかかるんで、
alistやvectorにして自己組織化探索やhashとかにした方がいいかも。
0173デフォルトの名無しさんNGNG
schemeばっかでlispの話題がでないね。
0174デフォルトの名無しさんNGNG
cons-streamとか、delay/forceって
有効に使ったことある人います?
無限ストリームとか、概念はカコイイんだけど、
いまいち使い道が・・
0175デフォルトの名無しさんNGNG
SICPに載ってるよ>174
訳はわかりずらいが。
0176デフォルトの名無しさんNGNG
なんでLispのコードを見ると関数がやたらグローバルなんだろう・・・。不思議だ。
0177デフォルトの名無しさんNGNG
>>176
やたらグローバルな本来の理由はわかりませんが、
こういう使い方はよくされる様です。
例えばcar cdrを再定義して、car cdrの入力のobjを呼ばれる度に
表示させたいとか、オリジナルを上書きした方が都合の良い場合。

;オリジナルのcar cdrを保存
(define orgcar car)
(define orgcdr cdr)
;car cdrを再定義
(define (car obj) (display* 'car ': " " obj "\n") (orgcar obj))
(define (cdr obj) (display* 'cdr ': " " obj "\n") (orgcdr obj))
;新しいcar cdrを使う
(car '(a b c))   ;=> car: a
(cdr '(a b c))   ;=> cdr: (b c)
; ....

;使い終わったらcar cdrを元に戻す
(set! car orgcar)
(set! cdr orgcdr)
0178デフォルトの名無しさんNGNG
;display*がcar/cdrを使うclosureの場合、
;>>177ではうまくいかない処理系があるかも
;つーわけで、
(define (car obj)
 (display 'car)
 (display ':)
 (display " ")
 (display obj)
 (display "\n")
 (orgcar obj))
(define (cdr obj)
 (display 'cdr)
 (display ':)
 (display " ")
 (display obj)
 (display "\n")
 (orgcdr obj))
0179デフォルトの名無しさんNGNG
;テスト
(map + '(1 2 3) '(4 5 6))
car: ((1 2 3) (4 5 6))
car: (1 2 3)
cdr: ((1 2 3) (4 5 6))
car: ((4 5 6))
car: (4 5 6)
cdr: ((4 5 6))
car: ((1 2 3) (4 5 6))
cdr: (1 2 3)
cdr: ((1 2 3) (4 5 6))
car: ((4 5 6))
cdr: (4 5 6)
cdr: ((4 5 6))
car: ((2 3) (5 6))
car: (2 3)
cdr: ((2 3) (5 6))
car: ((5 6))
car: (5 6)
cdr: ((5 6))
car: ((2 3) (5 6))
cdr: (2 3)
cdr: ((2 3) (5 6))
car: ((5 6))
cdr: (5 6)
cdr: ((5 6))
car: ((3) (6))
car: (3)
cdr: ((3) (6))
car: ((6))
car: (6)
cdr: ((6))
car: ((3) (6))
cdr: (3)
cdr: ((3) (6))
car: ((6))
cdr: (6)
cdr: ((6))
=>(5 7 9)
こうなります。traceがあればいらんけどね
0180デフォルトの名無しさんNGNG
>>174
delay/forceは、schemeで正規順序(ふつーのschemeの評価は作用的順序。)で
評価できる様にするもの。cons-streamはその応用。
(と、SICPに書いてありました)
有効な使い方は知りません(汗

(define (stream-car s) (car s) )
(define (stream-cdr s) (force (cdr s)))
(define (stream-ref s n)
 (if (= n 0)
  (stream-car s)
  (stream-ref (stream-cdr s) (- n 1))))

例)
無限に1が続くstream
(define ones (cons-stream 1 ones))
nをいくつにしても1が返る
(stream-ref ones n)

フィボナッチ数の無限ストリーム
(define (fibgen a b)
 (cons-stream a (fibgen b (+ a b))))
(define fibs (fibgen 0 1))

(stream-ref fibs 15)
=>610
(stream-ref fibs 30)
=>832040
0181デフォルトの名無しさんNGNG
>>177-178を適用した時のfibs 30の出力
(stream-ref fibs 30)
cdr: (0 . #<closure>)
cdr: (1 . #<closure>)
cdr: (1 . #<closure>)
cdr: (2 . #<closure>)
cdr: (3 . #<closure>)
cdr: (5 . #<closure>)
cdr: (8 . #<closure>)
cdr: (13 . #<closure>)
cdr: (21 . #<closure>)
cdr: (34 . #<closure>)
cdr: (55 . #<closure>)
cdr: (89 . #<closure>)
cdr: (144 . #<closure>)
cdr: (233 . #<closure>)
cdr: (377 . #<closure>)
cdr: (610 . #<closure>)
cdr: (987 . #<closure>)
cdr: (1597 . #<closure>)
cdr: (2584 . #<closure>)
cdr: (4181 . #<closure>)
cdr: (6765 . #<closure>)
cdr: (10946 . #<closure>)
cdr: (17711 . #<closure>)
cdr: (28657 . #<closure>)
cdr: (46368 . #<closure>)
cdr: (75025 . #<closure>)
cdr: (121393 . #<closure>)
cdr: (196418 . #<closure>)
cdr: (317811 . #<closure>)
cdr: (514229 . #<closure>)
car: (832040 . #<closure>)
=>832040
0182デフォルトの名無しさんNGNG
ウザイ。
0183デフォルトの名無しさんNGNG
schemeマンセー
0184デフォルトの名無しさんNGNG
構文の変換について質問なんですが、
(let ((a b) (c d)) e f)
は
((lambda (a c) e f) b d)
に書き換えられる事がわかったんですが、
ループ用の名前付きlet
(let loop ((a b) (c d)) (loop e f) )
は
((lambda () (define (loop a c) (name e f)) (loop b d)))
これよりもっと単純に置き換える事は可能でしょうか。
(define使わない方法とか)
0185デフォルトの名無しさんNGNG
まちがえました
((lambda () (define (loop a c) (loop e f)) (loop b d)))
0186デフォルトの名無しさんNGNG
lambdaの bodyにある defineは letrecの syntactic sugarにすぎないよな..

(letrec ((loop (lambda (a c) (loop e f)))) (loop a c)) か?

letrecはどうすんだろ。 lambda と set! で置き換えはできるけど。
0187デフォルトの名無しさんNGNG
>>186
逆だと思うのですが。
letrecがdefineとlambdaのsyntactic sugarと理解してます。
>>184
defeinは必ず必要だと思う。
0188184NGNG
>>186-187
無理ですかねぇ。
loopのclosureを引数にするとかでできないか、
もう少し考えてみます。

schemeはもしかすると、lambda(closure束縛)といくつかの
(syntax sugarではないset!とかの)特殊形式、if制御構文、
primitiveだけに変換できるのでは?〜と思ったんで。

#例えばconsやcar/cdrもlambda、if、eq?だけで表現できる。(効率は悪そうですが)
(下のcondはifのネストで変換)
;;;;cons
(lambda (l r)
(lambda (m)
(cond ((eq? m 'car) l)
((eq? m 'cdr) l)
(else (error "cons:" m)))
))
;;;;car
(lambda (z) (z 'car))
;;;;cdr
(lambda (z) (z 'cdr))
0189186NGNG
>>187 http://www.sci.toyama-u.ac.jp/~iwao/Scheme/r5rsj/html/r5rsj.html#SEC47
まあ構文糖とははっきり書かれてないけど。

http://www.sci.toyama-u.ac.jp/~iwao/Scheme/r5rsj/html/r5rsj.html#SEC81
に letrecを展開する macroとか書いてあるから、原理的に okだが。
macroわすれた。
0190184NGNG
>>199
なるほど、named-let->letrec->let->lambdaって風に
変換するみたいですね。手変換できるかも。ありがとうございます。
マクロはlispのdefine-macro形式ならわかるけど、
let-syntaxとかの構文はいまだに謎・・。
なんであれがschemeの標準マクロなのか不思議です。
0191184NGNG
とりあえず手変換ですがなんとか出来ました。
やっぱりclosureを引数に取る方法でいけました。
(1)、(2)でclosureを呼出してると同時に、自分自身の束縛も引数に入れてるのが肝です。
これを形式変換するには、(1)はテンプレート変換で良いとして、
(2)は、named-let中に置かれた(loop ...)呼出しを探して、
(loop loop ...)形式に置き換えないといけないから、環境生成の監視
を伴うので結構面倒そうです。(シンボルがバッティングしない様にしたり)
(loop ...)形式のままで変換できれば一番良いんですが・・。

(let loop ((a b) (c d)) (loop e f) )
↓
((lambda (a c)
 ((lambda (loop) ;   …(1)
  (loop loop a c))
  (lambda (loop a c) ; …(2)
   (loop loop e f)
  )))
 b d)
0192186NGNG
>>191 確かにうまくいってそうな気がする。だまされてるような気もする。
でも R5RSじゃ、やっぱり環境つくって set! してるみたいだ。
その方が素直だろ。letrecっつう関数型っぽいもので set!が出てくるのは
癪だけど。

確か R5RSの macroは hygenic(清潔?) っつーのが売りだったような。
Lispの macroだと新しく導入した symbolが既存の物とぶつかることもあるって
のが不潔なんだろうな。でも internしなきゃいい気もするが。忘れた。
0193184>192NGNG
>だまされてるような気もする。
>>191は一応他の形式でもテストしたんで動きますよ(汗
named-let->letrec->lambda変換(set!を使う)の方だと
>>191の方法と違って環境探索が必要無いので、
素直に定型テンプレートで形式変換できますね。
((lambda (loop)
 (set! loop
  (lambda (a c)
   (loop e f)
  ))
(loop b d)
())
どのみちset!は必要だから、こっちの方がいいのかな。

>hygenic(清潔?) っつーのが売りだったような。
schemeのマクロはlispなら(gensym)で回避する問題を
自動でやってくれるって事ですか。
使いこなせればかなり便利そうですね。
(日本語の資料が不足ぎみ・・)
0194184>NGNG
>>191の方法を使ったふぃぼなっち
(define fib3
 (lambda (n)
  ((lambda (fib-iter)
   (fib-iter fib-iter 1 0 n))
   (lambda (fib-iter a b c)
   (if (= c 0)
    b
    (fib-iter fib-iter (+ a b) a (- c 1))
   )
  )))
)
(fib 30)
=>832040
0195デフォルトの名無しさんNGNG
syntax-caseってなんでしょう。
これもマクロかな?
0196デフォルトの名無しさんNGNG
ageておく
0197デフォルトの名無しさんNGNG
現在ある言語の中でどれが最高?スレの133へ
(他スレからの引用の仕方ってあるんですか?)

>マクロって参照を使える言語での関数定義とほとんど同じようなもんだろ?
>Cの関数定義では、絶対に同等のことが出来ないようなマクロって
>例えばどんなやつ?

決定的に違うのは、
・マクロ生成時に文脈を調べて生成方法を変えられる。
・マクロを解釈するコードは「プリプロセッサ」としての式ではなく、lisp関数群がそのまま使える。
・展開後のマクロはマクロとしてではなく、普通のlispコードと同じレベルで扱える。

例はとりあえず、オンラインにあるやつ見てください。
(define-macro defmacro macroで検索)
0198133NGNG
>・マクロ生成時に文脈を調べて生成方法を変えられる。
なるほど。

> ・マクロを解釈するコードは「プリプロセッサ」としての式ではなく、lisp関数群がそのまま使える。
例えばfun(int,int){}内ではC関数群はそのまま使えると思うが?

> ・展開後のマクロはマクロとしてではなく、普通のlispコードと同じレベルで扱える。
fun();という文はCコードと同じレベルではないのか?
0199デフォルトの名無しさんNGNG
マクロは通常、随時解釈されますが、
マクロを展開してコードに直接埋め込む事ができます。(破壊操作)
また、元コードを保ちたい場合、展開コードをキャッシュして持っておく様にもできます。
0200デフォルトの名無しさんNGNG
>>198
Cでいうなら、#define内で「マクロ生成の為だけの」コードを
書けるということなんですが。
(展開コードには余計なものは含まれません。)
これは実際に触わってみないと判らないかもしれない。
0201133NGNG
>>199
> マクロを展開してコードに直接埋め込む事ができます。(破壊操作)

何らかのコード;
fun();
何らかのコード;

という部分があれば、fun();が埋め込まれてるんじゃないのか?
変数を渡したい場合はポインタのようなもので渡さなきゃいけないが。

> また、元コードを保ちたい場合、展開コードをキャッシュして持っておく様にもできます。

何らかのコード;
if (保ちたくない場合)
fun();
何らかのコード;

とは違うのか?
0202133NGNG
>>200
うーむ。#defineの中で本当のコードが使えるということか?
LISPは本で少し読んだだけだが、ふと疑問に思ったもんで。
まあ、マクロはもっと勉強してみます。
ありがとう。
0203デフォルトの名無しさんNGNG
例えば、
#define myif(test, t, f) \
if (nullp(f)) printf("if (%s) %s ", test, t);
else printf("if (%s) %s else %s", test, t, f);
としたときのprintfの出力がそのままコンパイルの段階で
コードに埋め込まれるという感じに少し似ているかな?
printfの文字列の部分が展開テンプレート、
printfの出力が展開コード、
printfやif-elseの部分はマクロ解釈コード。
0204133NGNG
>>203
そういうのって、
myif(int a, void (*b)(),void (*c)()){
if (a)
b();
else
c();
}

じゃやっぱ駄目かね…
myif使うたびに関数が増えるのがちょっと面倒だけど。
0205デフォルトの名無しさんNGNG
おもしろage
0206デフォルトの名無しさんNGNG
http://www.shiro.dreamhost.com/scheme/trans/beating-the-averages-j.html
0207デフォルトの名無しさんNGNG
call/cc (call-with-current-continuation) の使い方その3

while文 (break continue 付き)
(while test body .. )

C言語の繰返し制御構文whileと互換の物を作成します。
test式の評価結果が真の間、bodyシーケンスを繰返し実行します。
whileブロックからの戻り値は特に規定しない事にします。
0208デフォルトの名無しさんNGNG
実装方法(1/2)
while文自体の定義は簡単です。
普通にマクロで定義するとこうなります。

(define-macro (mywhile0 test . body)
 (let ((loop (gensym)))
  `(let ,loop ()
   (cond
    (,test
     ,@body
     (,loop)))
  )))

ただしこの定義ではnamed-letのsyntax-sugarとしての役割しかなく、
Cで使えるbreakやcontinueといった脱出構文が使えません。
そこで、継続を使用してwhileのbody内で(break)や(continue)と
いった記述を出来るようにします。
0209デフォルトの名無しさんNGNG
実装方法(2/2)
body内で、継続を束縛したシンボル(break、continue)を直接参照するには、
bodyをその継続ブロック内に置く必要があります。
breakはループの外側の階層に置くことで、(break)を呼出すとループの直後に抜ける事が出来ます。
また、continueはtestの直後、bodyの外側の階層に置くことで機能を果します。

(define-macro (mywhile test . body)
 (let ((loop (gensym)))
  `(call/cc (lambda (break)
   (let ,loop ()
    (cond
     (,test
     (call/cc (lambda (continue)
      ,@body
     )) ; call/cc continue
     (,loop)))
   ))) ; call/cc break
 ))
0210デフォルトの名無しさんNGNG
;テスト
(define (make-step-list from to inc)
 (let loop ((i from))
  (if (= i to)
    '()
    (cons i (loop (inc i))))
 ))

(define-macro (mypop s)
 `(if (pair? ,s)
    (prog1 (car ,s) (set! ,s (cdr ,s)))
    #f))

(define (mywhile-test)
 (define step (make-step-list 0 20 (lambda (i) (+ i 1) )))
 (mywhile
  (pair? step)
  (display (car step)) (display #\space)
  (if (= 16 (car step))
   (break))
  (mypop step)
  (if (not (= 1 (% (car step) 2) ))
   (continue))
  (mypop step)
 )
 (display 'end) (newline)
 #t
)
0211デフォルトの名無しさんNGNG
;テスト結果
(mywhile-test)
0 2 4 6 8 10 12 14 16 end
=>#t
0212デフォルトの名無しさんNGNG
(a) -> aを関数と見立てて評価
a -> aに束縛されたオブジェクト
'(a) ->(a)というリスト
'a ->aというシンボル
便利だね。
シンボルはそのまま表示できるし。
(display 'a)
0213デフォルトの名無しさんNGNG
>>212
symbol->stringかなんかで"a"の様に文字列にすると、
生成するたんびにその分のメモリを消費するから、
シンボルは引用符を付けて表示させるのが良い。
シンボルなら同一性のテストが低コストで行なえるし。
0214213NGNG
>低コストで行なえるし。
*確実に*低コストで行なえるし。
のまちがい。
0215デフォルトの名無しさんNGNG
可能性を感じさせる言語だ
0216デフォルトの名無しさんNGNG
内部定義やlambdaで簡単に外側の変数いぢれるのがいいね
(let ((x 0))
 (map (lambda (i) 〜xの操作 ) list)
)
0217デフォルトの名無しさんNGNG
(let ((x 3)) (funcall #'(lambda () (* x x))))
0218デフォルトの名無しさんNGNG
http://piza.2ch.net/test/read.cgi?bbs=tech&key=989508360&st=147&to=147&nofirst=true
累算変数ってなんですか?
0219デフォルトの名無しさんNGNG
累積変数ってのは、末尾再帰に直すときに使われる技法だな。
(define (sum xs)
(if (null? xs) 0 (+ (car xs) (sum (cdr xs)))))
って素直だけど stackを消費する再帰を
(define (sum xs)
(define (isum xs r)
(if (null? xs) r (isum (cdr xs) (+ r (car xs)))))
(isum xs 0))
って、rって変数を使って末尾再帰に直す事。
っていうか、変数r そのものが累積変数。だと思われ。
0220218NGNG
>>219
ありがとうございます。
なるほど。結果を保存しておく一時変数の事ですか。
こういうのって、機械が末尾再帰じゃない再帰を見つけて、可能なら末尾再帰に
直すとかしてくれると助かりますよね・・。
人間ならちょっと考えれば可能だけど、機械にやらせるとなるとしんどいかな。

(define (sum xs)
 (if (null? xs)
   0
   (+ (car xs) (sum (cdr xs)))
 ))

;↓(内部定義へ変換)
(define (sum2 xs)
 (define (isum r xs)
  (if (null? xs)
    r
    (isum (+ r (car xs)) (cdr xs))
  ))
 (isum 0 xs))
または
;↓(named-letへ変換)
(define (sum3 x)
 (let isum ((r 0) (xs x))
  (if (null? xs)
    r
    (isum (+ r (car xs)) (cdr xs))
  )))
この例は簡単だけど、パターン化できないかな。
0221デフォルトの名無しさんNGNG
最初はこういう形式変換からかな。
このパターンの時
(rec xs)
(null? xs) => 0
(operator (car xs) (rec (cdr xs))) =>result
↓
変数rを使用して下のパターンに変換
r := 0
(rec r xs)
(null? xs) => r
(rec (operator r (car xs)) (cdr xs)) =>result

一次変換
(define (sum r xs)
 (if (null? xs)
   r
   (sum (+ r (car xs)) (cdr xs))
 ))
(sum 0 '(1 2 3 4))
=>10
0222デフォルトの名無しさんNGNG
(define (foldr bop defval xs)
(if (null? xs)
defval
(bop (car xs) (foldr bop defval (cdr xs)))))

(define (foldl bop defval xs)
(if (null? xs)
defval
(foldl bop (bop defval (car xs)) (cdr xs))))

bop が可換なら (foldr bop defval xs) と (foldl bop defval xs) は等価
foldl は末尾再帰 ?
0223デフォルトの名無しさんNGNG
>>222
>foldl は末尾再帰 ?
見た感じそのようですが。
末尾再帰であるかの判定は、
foldrは、bopに与える被演算子がfoldr再帰の結果なのでそれが求まるまでbopの評価を遅延する必要がある。よって普通の再帰。
foldlは、foldl再帰の結果が関数の値そのものになるので遅延させるべき演算は存在しない。よって末尾再帰。
という風に考えれば良いんじゃないかと。
ifが絡みますが、ifは分岐構文であって、分岐先が決まったら、保存する様な状態が無いことからfoldlが末尾再帰である事の証明への妨げにはなりません。
0224デフォルトの名無しさんNGNG
これも末尾再帰
(define (countdown5 s)
 (cond
  ((= 0 s) s)
  ((= 1 s) (display s) (countdown5 (- s 1)))
  ((= 2 s) (display s) (countdown5 (- s 1)))
  ((= 3 s) (display s) (countdown5 (- s 1)))
  ((= 4 s) (display s) (countdown5 (- s 1)))
  ((= 5 s) (display s) (countdown5 (- s 1)))
  (else (countdown5 (- s 1)))
 ))

(countdown5 10)
54321
=>0
0225デフォルトの名無しさんNGNG
>>223
なる
0226デフォルトの名無しさんNGNG
call/cc (call-with-current-continuation) の使い方その4
for文
(for init test incr body ...)

test body はwhileの時と同じ。initとincrが増えただけ。
initとincrにはfor内部で参照するカウンタ変数の初期化式と増減式を記述します。
initで(i 0) とすれば、iがカウンタ変数(初期値0)として使用されます。
initで宣言したカウンタ変数はtest/incr/body内で参照できます。
0227226NGNG
(続き)
この例では、named-letの書式をそのまま当てはめて使用してるので、letと同じ
問題を含んでいます。(よって実際のC言語のfor文より使い勝手は落ちます。)
initとincrに与える書式は、
init が () の時、 incr は () (==whileと同じ意味)
init が (x 0) の時、 incr は (+ x 1)
init が ((x 0) (y 1) (z 2)) の時 incr は ((+ x 1) y (+ z y))
を許します。
let束縛順序の規則が適用されるので、initに((x 0) (y x) (z y)) の様な式は書けません。
(被演算子側の x, yは外部に存在する物と解釈されます。)

これらの書式の判定と選択はマクロ解釈コード内で行ないます。
出力の展開コードには含まれません。
for-expand内部定義の場合分けを増やす事によって、柔軟な構文を許す事ができます。
0228226NGNG
;実装
(define-macro (for init test incr . body)
 (let ((loop (gensym))
    (expand-init
     (if (or (null? init)
         (pair? (car init)))
       init
       (list init)) )
    (expand-incr
     (if (or (null? init)
         (pair? (car init)))
       incr
       (list incr)) ))

  `(call/cc (lambda (break)
    (let ,loop ,expand-init
     (cond
      (,test
      (call/cc (lambda (continue)
       ,@body
      )) ; call/cc continue
      (,loop ,@expand-incr)))
    ))) ; call/cc break
 ))
0229226NGNG
;おまけ
;letが大袈裟だと思ったときに使う。
(define-macro (tmp init . body)
 (let ((expand-init
     (if (or (null? init)
         (pair? (car init)))
       init
       (list init)) ))
  `(let ,expand-init ,@body)
 ))

;forのテスト
(define (九九 from to)
 (for (y from) (<= y to) (+ y 1)
  (for (x from) (<= x to) (+ x 1)
   (tmp (n (* x y))
    (if (< n 10) (display #\space))
    (if (< n 100) (display #\space))
    (display* n #\space)
   )
  )
  (display* eol)
 ))
0230226NGNG
;テスト結果
(九九 1 9)
 1  2  3  4  5  6  7  8  9
 2  4  6  8 10 12 14 16 18
 3  6  9 12 15 18 21 24 27
 4  8 12 16 20 24 28 32 36
 5 10 15 20 25 30 35 40 45
 6 12 18 24 30 36 42 48 54
 7 14 21 28 35 42 49 56 63
 8 16 24 32 40 48 56 64 72
 9 18 27 36 45 54 63 72 81
=>()
0231226NGNG
ずれちゃった・・
補足:
マクロの展開処理は普通のlispの記号処理と同程度のコストが掛かるので、
記述が長くなると不利ですが、コンパイラや直コード埋め込み、マクロキャッシュ
などを持っている処理系ならば、実行時に展開を行なう回数は0〜1回に抑える
事ができます。
(逆を言えば、これらの機能の無い処理系上ではマクロを積極的に使うことは考えられない。)
0232226NGNG
;おまけ C言語のpre/post ++ --をエミュレートするマクロ
(define-macro (pre++ bind) `(begin (set! ,bind (+ ,bind 1)) ,bind))
(define-macro (post++ bind) `(prog1 ,bind (set! ,bind (+ ,bind 1))))
(define-macro (pre-- bind) `(begin (set! ,bind (- ,bind 1)) ,bind))
(define-macro (post-- bind) `(prog1 ,bind (set! ,bind (- ,bind 1))))
0233226NGNG
call/cc (call-with-current-continuation) の使い方その5

do〜while文
(do- body -while test)

Cの繰返し制御構文do〜whileと互換の物を作成します。
既にdo文というものが存在するので、代わりに
do- -whileシンボルを使用します。-whileはダミーシンボルです。
ダミーシンボル自体には意味はありませんが、
ここでは簡単な構文チェックに使用しています。
0234226NGNG
;実装
(define-macro (do- body dmy test)
 (let ((loop (gensym)))
  (if (not (eq? dmy '-while))
   (error "do- -while abnormal syntax : do-" dmy))
  `(call/cc (lambda (break)
   (let ,loop ()
    (call/cc (lambda (continue)
     ,@body
    )) ; call/cc continue
    (cond
     (,test
      (,loop)))
   ))) ; call/cc break
 ))
0235226NGNG
;テスト
(tmp (x 0)
 (do-
  (display* x eol)
  (pre++ x)
 -while (= x 10))
)
error: do- -while abnormal syntax : do- (pre++ x)

(tmp (x 0)
 (do- (
  (display* x eol)
  (pre++ x)
 ) -while (= x 10))
)
0
=>()
0236デフォルトの名無しさんNGNG
参考になりました。>>226
whileは検索で見つかるんだけど、forとかのサンプルって何処にも無いんだよね。
call/cc含めたやつなんか皆無だった。
使ってる人はどうしてるのかな?
0237デフォルトの名無しさんNGNG
たしかに(C風の)forやdo-whileのサンプルなんて全然おちてないみたいね。
Cユーザー層向けにRxRSにでもマクロサンプルとか置いといてくれないかなあ。
(define-macroはvanilla Lisp styleだけど。)
0238デフォルトの名無しさんNGNG
for (i = list; pairp(i); i = cdr(i)) {
 putatom(car(i));
}
(for (i '(a b c d)) (pair? i) (cdr i)
 (display (car i)))
うむ、似た書式で書けるのはやっぱ便利。
0239デフォルトの名無しさんNGNG
forに相当する構文は、もともとdoってのがあるが。
だから見つからないだけだろう。

それになれてくると使わなくなってくるしな。
0240デフォルトの名無しさんNGNG
よく知らないけど、マクロって言うのは
Lispにしかないの?

Cとかと違って、意味論的には汚くならないの?
0241デフォルトの名無しさんNGNG
>>239
doって書式わかりずらくないですか?括弧も多くなるし。
(do ((var init incr)) (test result) body)
for文はC知ってる人なら多分とっつきやすいでしょうね。
c->scheme変換の時も楽だし。(c->schemeする意味自体はともかく)
doのresultに相当する部分が無いのは結構致命的ですけど。
慣れるとdoすら必要ない気がするのは同意。
0242デフォルトの名無しさんNGNG
(for (set! i list) (pair? i) (set! i (cdr i))
 (print (car i)))
とかのがよさげ?
0243デフォルトの名無しさんNGNG
あのforはわざわざ破壊的代入を避けて実装されてるのに、なぜにset!?>242
0244デフォルトの名無しさんNGNG
>>241
わかりずらいのでfor-eachとかmapしか使わなくなってくるんだな。
一度closure使って数列発生器作っとけば
for-eachをcのfor的に汎用的に使えるんじゃないのかね。
0245デフォルトの名無しさんNGNG
>240
schemeにはもっと高級なのがあります。
(パターンを記述する形式。わたしは良く知りません)
lispのdefine-macro形式は実現が簡単だという理由で、
ほぼ全ての処理系に付いてます。
(evalとapply部でフックできれば自作できる程度。多分・・。)
0246デフォルトの名無しさんNGNG
fluid-letについて知ってる人いませんか?
fluid bindings
dynamic-windと関係あるみたいなんですが。
0247デフォルトの名無しさんNGNG
ここ読んでもよくわからなかった。(動的スコープがなんたら。)
http://srfi.schemers.org/srfi-15/srfi-15.html
普通に使ってるぶんには関係ないのかな?
0248デフォルトの名無しさんNGNG
do- -while修正
(do- body-expr -while test-expr)
(do- ((lambda (p) ) rp) -while test-expr) の場合に動作しない。
body-exprに複文を置きたい場合は↓の様にする。
(do- (begin ...) -while test-expr)

(define-macro (do- body dmy test)
 (let ((loop (gensym)))
  (if (not (eq? dmy '-while))
   (error "do- -while abnormal syntax : do- " dmy))
  `(call/cc (lambda (break)
   (let ,loop ()
    (call/cc (lambda (continue)
     ,body
    )) ; call/cc continue
    (cond
     (,test
      (,loop)))
   ))) ; call/cc break
 ))
0249デフォルトの名無しさんNGNG
>>241
>(c->schemeする意味自体はともかく)
意味自体は結構あると思う。
括弧が減るってだけで可読性かなり良くなるし。
ありがと〜。
0250デフォルトの名無しさんNGNG
>>247
fluid-letした変数は同名の変数をマスクしてdynamic scopeのように振舞う上に、
再びfluid-letのスコープに入ると前に入ったときの値が残っているというわけか。
例を見たほうがわかりやすいな。でもこのsfriはwithdrawnだよ。
0251250NGNG
sfri -> srfi
0252デフォルトの名無しさんNGNG
(define (fib n)
  (define (iter a b p q count)
    (define (even? n) (= (% n 2) 0))
    (cond ((= count 0) b)
          ((even? count)
           (iter a
                 b
                 (infix q * q + p * p)
                 (infix 2 * p * q + q * q)
                 (infix count / 2)))
          (else (iter (infix b * q + a * q + a * p)
                      (infix b * p + a * q)
                      p
                      q
                      (infix count - 1))
          )))
  (iter 1 0 0 1 n))
0253デフォルトの名無しさんNGNG
list構造を再帰的に辿って、atom以外を全て複製したい場合が出てきました。
全てのconsで作られたセルを複製する関数って標準でありますか?
↓みたいなやつ。あればそっちを使いたいんですが。
  
(define list-dup (lambda (l)
  (let loop ((x l))
    (cond ((null? x) x)
          ((pair? x) (cons (loop (car x))
                           (loop (cdr x))))
          (else x)))))
0254デフォルトの名無しさんNGNG
あ、やっぱりいいです
0255デフォルトの名無しさんNGNG
lispはいーかげんなデータ構造簡単に作れるからいいね。
それを探索するのも簡単だし。
0256246NGNG
>>250
ありがとうございます。
結局自分では使わなさそうということが分かりました。
0257デフォルトの名無しさんNGNG
(deine f (lambda x 〜))
ってやると
(f a b c d )
(car x) -> a
(cadr x) -> b
(caddr x) -> c
(cadddr x) -> c
って書けるのね。
(deine (f . x) ...)
の意味がようやく理解できたyo
0258デフォルトの名無しさんNGNG
age
0259デフォルトの名無しさんNGNG
誰か質問に答えてくれる人います?
0260デフォルトの名無しさんNGNG
質問の内容による
0261デフォルトの名無しさんNGNG
なんで set! は setq と違って、代入した値を
返してくれないの?
0262>261NGNG
未定義だと決まってるから、としか言えない。
なぜ未定義にしたかは、仕様を決めた人に聞くしかない。
(理由を知ってる人がいたら解説お願いします。)
代入値をそのまま返す処理系はあるとは思うけど、
どの処理系でも確実に代入値を返したいなら、
マクロで定義する方法がある。
(define-macro (myset! sym expr)
`(begin (set! ,sym ,expr) ,sym))
=>myset!

(define a 0)
=>a
(myset! a (+ a 1))
=>1
0263デフォルトの名無しさんNGNG
(define := myset!)
=>:=
(infix-operator (cons := 'right))
;infix解析器に:=を右結合で登録

(infix a := a + 1)
---->(eval (begin (set! a (+ a 1)) a))
=>1
0264デフォルトの名無しさんNGNG
(infix a ;= b := a + 1)
---->(eval (begin (set! a (begin (set! b (+ a 1)) b)) a))
か?
0265デフォルトの名無しさんNGNG
マクロってapplyできるの?
0266デフォルトの名無しさんNGNG
>>265
普通できるんじゃないの?
(define a 0)
(apply myset! `(a ,(a + 1)))
=>1
a
=>1
0267デフォルトの名無しさんNGNG
まちがった
(apply myset! `(a ,(+ a 1)))

しかしこの場合マクロキャッシュが働くか疑問
0268デフォルトの名無しさんNGNG
あ、マクロだから普通のquoteでもいいのか。
(apply myset! '(a (+ a 1)))
0269デフォルトの名無しさんNGNG
>>265
lispでは(Common Lispの仕様書によると)できないみたいね。
0270デフォルトの名無しさんNGNG
schemeハァハァ
0271デフォルトの名無しさんNGNG
話題止まっちゃったね。
誰かネタ振り希望。
0272デフォルトの名無しさんNGNG
スマソ LIPS スレと間違った。
0273デフォルトの名無しさんNGNG
ネタ提供ありがとうございました。
0274ネタ提供しますNGNG
剥いたみかん→((()))
0275デフォルトの名無しさんNGNG
( ´-`)
0276デフォルトの名無しさんNGNG
剥く前のみかん(:*:)
0277デフォルトの名無しさんNGNG
ネタ提供
>>226-231 のforの展開内容をリストで確認できる様にしたもの。

(for-expand '(a) 'b '(c) '(d e f))
=>(call/cc (lambda (break)
    (let G22 ((a))
      (cond
        (b
          (call/cc (lambda (continue) d e f))
          (G22 (c)))))))
0278277NGNG
(define (for-expand init test incr body)
  (let ((loop (gensym))
        (expand-init
          (if (or (null? init)
                  (pair? (car init)))
              init
              (list init)) )
        (expand-incr
          (if (or (null? init)
                  (pair? (car init)))
              incr
              (list incr)) ))

    `(call/cc (lambda (break)
       (let ,loop ,expand-init
         (cond
           (,test
            (call/cc (lambda (continue)
              ,@body
            ))
            (,loop ,@expand-incr)))
       )))
  ))

;for-expand の結果をそのままマクロに適用する
(define-macro (for init test incr . body)
   (for-expand init test incr body)
)
0279デフォルトの名無しさんNGNG
(define (while-expand test body)
  (let ((loop (gensym)))
    `(call/cc (lambda (break)
      (let ,loop ()
        (cond
          (,test
          (call/cc (lambda (continue)
             ,@body
          ))
           (,loop)))
      )
    ))
  ))

(define-macro (while test . body)
  (while-expand test body))
0280デフォルトの名無しさんNGNG
(define (do-while-expand body dmy test)
  (let ((loop (gensym)))
   (if (not (eq? dmy '-while))
     (error "do- -while abnormal syntax : do- " dmy))
   `(call/cc (lambda (break)
      (let ,loop ()
        (call/cc (lambda (continue)
          ,body
        ))
        (cond
          (,test
           (,loop)))
      )))
  ))

(define-macro (do- body dmy test)
  (do-while-expand body dmy test))
0281デフォルトの名無しさんNGNG
展開前
(define (example0 from to r p)
  (for (i from) (<= i to) (+ i 1)
    (if (< 0 r)
        (if (not (memv i p))
           (example0 from to (- r 1) (cons i p)))
        (begin
          (disp-rev p)(display " ")
          (break)
        ))))

展開後
(define (example0 from to r p)
  (call/cc
    (lambda (break)
      (let G22
        ((i from))
        (cond
          ((<= i to)
            (call/cc
              (lambda (continue)
                (if (< 0 r)
                  (if (not (memv i p))
                    (example0 from to (- r 1) (cons i p)))
                  (begin
                    (disp-rev p)(display " ")
                    (break)))))
            (G22 (+ i 1))))))))
0282デフォルトの名無しさんNGNG
format作ってくれ。Common Lispにあるようなやつ。
0283デフォルトの名無しさんNGNG
named-let/condの展開
(define example0
  (lambda (from to r p)
    (call/cc
      (lambda (break)
        ((lambda (G22)
           (set! G22
  (lambda (i)
    (if (<= i to)
      (begin
        (call/cc
          (lambda (continue)
            (if (< 0 r)
              (if (not (memv i p))
                (example0
                  from
                  to
                  (- r 1)
                  (cons i p)))
              (begin
                (disp-rev p) (display " ")
                (break)))))
        (G22 (+ i 1))))))
           (G22 from))
          ())))))
0284デフォルトの名無しさんNGNG
>282
SLIBに入ってるよ
printf/scanf系も
0285デフォルトの名無しさんNGNG
入ってた。1700行ぐらいある。作るのは結構大変かも。
0286デフォルトの名無しさんNGNG
上のexample0はここにあったやつをforに書き直したもの
http://piza.2ch.net/test/read.cgi?bbs=tech&key=989929288&st=853&to=853&nofirst=true
0287デフォルトの名無しさんNGNG
syntax-sugarを実際に展開できる言語マンセー
0288デフォルトの名無しさんNGNG
>>286
そのレスのC言語での解答(かわいそうなので)
#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
int memv_int(int k, int *a, size_t an) {
    int i = 0;
    for (i = 0; i < an; i++)
        if (k == a[i])
            return 1;
    return 0;
}

void disp(int *a, size_t n) {
    int i;
    for (i = 0 ; i < n; i++)
        printf("%d", a[i]);
}

void example0(int n, int r, int *a, size_t an) {
    int i;
    for (i = 1; i <= n; i++)
        if (r) {
            if (!memv_int(i, a, an)) {
                a[an++] = i;
                example0(n, r - 1, a, an);
                an--;
            }
        } else {
            disp(a, an);
            printf(" ");
            break;
        }
}

void example(int n, int r) {
    int *a = malloc(sizeof(int) * r);
    assert(a);
    example0(n, r, a, 0);
    free(a);
}

int main(int argc, char **argv) {
    assert(argc == 3);
    example(atoi(argv[1]), atoi(argv[2]));
    printf("\n");
    return 0;
}
0289デフォルトの名無しさんNGNG
良く見たらバックトラックの問題だねえ
0290デフォルトの名無しさんNGNG
結果をリストで得られる様にした物
(define (example efrom eto er)
  (let eloop ((from efrom) (to eto) (r er) (p '()))
    (let loop ((i from))
      (cond ((<= i to)
         (cond ((< 0 r)
           (if (not (memv i p))
             (let ((l (eloop from to (- r 1) (cons i p))))
               (if (and (pair? l) (pair? (car l)))
                   (append! l (loop (+ i 1)))
                   (cons l (loop (+ i 1)))))
             (loop (+ i 1))))
               (else (reverse p))))
       (else '())))))

(example 1 3 3)
=>((1 2 3) (1 3 2) (2 1 3) (2 3 1) (3 1 2) (3 2 1))
0291デフォルトの名無しさんNGNG
>>202
> うーむ。#defineの中で本当のコードが使えるということか?

式が「実行時に」2回evalられると思えばよい。
よって、2度目にevalられる式を「生成する」式を書く。
一方、Cのマクロは翻訳時にしか展開されないし、単なる文字列展開に近い。
C++のtemplateは、翻訳時に整数計算できるけど。(よって翻訳時再帰展開可)

こういうのは、

>>240
> よく知らないけど、マクロって言うのは
> Lispにしかないの?

式自体が、first-class objectであるような言語でないと難しい。
Prologにもマクロを持っている奴がいる。(Lisp:Prolog=S式:節)
0292デフォルトの名無しさんNGNG
マクロを応用すると、例えばdefine-with-expand-macroというマクロを定義する事により、
人間が定義した全てのマクロやインライン展開可能なコードを全て
展開した結果に対して定義できたりします。
(define-macro (define-with-expand-macro ...))

(define-with-expand-macro name (lambda () (マクロを使った定義)...))
↓
(define name (lambda () 展開コード))
これはマクロ展開キャッシュの無い処理系にとっては速度アップに繋がります。
またキャッシュバッファの大きさを気にする必要もなくなります。
(その代わりコード量は増大しますが)

例)マクロが含まれた定義(infixや(if- else-if else)はマクロとします)
(define-with-expand-macro (fib4 n)
  (define (even? n) (infix n & 1 = 0))
  (define (fib4-iter a b p q count)
    (if- (infix count = 0)
         b
     else-if (even? count)
             (fib4-iter a
                        b
                        (infix q * q + p * p)
                        (infix 2 * p * q + q * q)
                        (infix count >> 1))
     else    (fib4-iter (infix b * q + a * q + a * p)
                        (infix b * p + a * q)
                        p
                        q
                        (infix count - 1))
    )
  )
  (fib4-iter 1 0 0 1 n))
0293デフォルトの名無しさんNGNG
↓
define-with-expand-macroは、
マクロ展開結果を直接埋め込んだコードに変換したdefineを評価する
(define (fib4 n)
  (define (even? n)
    (= (& n 1) 0))
  (define (fib4-iter a b p q count)
    (if (= count 0)
      b
      (if (even? count)
        (fib4-iter
          a
          b
          (+ (* q q) (* p p))
          (+ (* 2 p q)
             (* q q))
          (>> count 1))
        (fib4-iter
          (+ (* b q)
             (* a q)
             (* a p))
          (+ (* b p) (* a q))
          p
          q
          (- count 1)))))
  (fib4-iter 1 0 0 1 n))
0294デフォルトの名無しさんNGNG
これが出来て何が嬉しいのかというと、人間側から見て、
より判りやすい様に納得がいくまで構文をカスタマイズできる事です。
(if- else-if elseマクロは、condと同等で、より括弧の数が少ない構文を作る)
(infixは中置記法を許すマクロ)

また、マクロを全て展開して埋め込む事で、インタプリタ上でも実行効率が損なわれない。
(lispではマクロもlispコードの一種なので、馬鹿正直に実行時に展開すると、結構なコストが掛かる。)
(キャッシュを持っていても、バッファから溢れたマクロは再評価されるので効率的ではない。)
0295デフォルトの名無しさんNGNG
define-with-expand-macroみたいなの使うと
マクロが評価されるとき(すなわちdefineする前)
に構文チェックするハンドラ関数も呼出せるのでお得。
ここでまじめにチェックしておくと、実行時エラーになる
コードを減らす事ができる。
0296デフォルトの名無しさんNGNG
でもさあ、lazy evaluation+カリー化関数で、マクロとそっくりに
ならない?
my_ifも、 引数三つ取る関数とかにしてさ…
lazy evaluationなら、三つ目の引数は評価しないとか出来るし。
0297295NGNG
>>296
遅延評価は良く知りませんが、
恐らく(見掛け上)マクロと同様に、引数をapplyしないで得られるって事ですよね?
delayは積極的に使ったことが無いのでそういう方法がある事を思い付きませんでした。
後で実験してみます。
0298デフォルトの名無しさんNGNG
sage
0299デフォルトの名無しさんNGNG
>>296
良く考えたら遅延評価でできると言っても、
delayに渡すまでにどこかで評価されちゃうんじゃ?
それともこういうことですか?

(define (myif test true false)
(if (test) (true) (false)))

(myif
(lambda () #t)
(lambda () #t)
(lambda () #f)
)
0300デフォルトの名無しさんNGNG
=>#t
0301デフォルトの名無しさんNGNG
>>296
マクロの代わりにはならないと思う。
単に、
(関数 引数 引数 引数 ...)
をapplyを通さずにリストとして得られるって事なので。
(もし遅延評価+カリーで出来たとしても冗長なコードになる筈。)
0302デフォルトの名無しさんNGNG
ある無名の書評者の文章より。
http://www.amazon.com/exec/obidos/tg/stores/detail/-/books/0262011530/customer-reviews/8/002-7400680-3044044?show=-submittime

This is very deep material for a programming
newbie to learn outside a course, but for an
experienced nerd who's looking for a systematic
framework, it's absolutely terrific. I had done
lots of lisp and compiler work before reading
the book, so many of the concepts were not new.
But it's with this framework in mind that I learn
new technologies, and this approach greatly speeds
up how long it takes to understand each week's "new"
hot product/language/tool/mindset. Put another way:
why do so many popular computer books take 1000 pages
to describe a few trivial concepts?

これ読んでXML関連スレから流れて来ました。よろしくお願いします。
0303デフォルトの名無しさんNGNG
XML=LISPの方言
0304デフォルトの名無しさんNGNG
>>301の書評ページみると、SICPを「プログラム書法」かなにかと間違えて
購入した人がたくさんいるみたい。
0305デフォルトの名無しさんNGNG
>>304
ガイジンは購入する前にどんな本か目次でも見て確認しないのですか?
0306ガイジンNGNG
ソウデザゴイスマ。>>305
0307デフォルトの名無しさんNGNG
XMLって何がすごいんだろう?
あのタグって読みにくいから、LISPみたいに、括弧でくくる方が見やすいと思うんだけどなぁ〜。
それならLISPの資産がそのまま使えるのに。
DOMもcarやcdr、consで十分だし、こっちの方がカッコいいと思うんだけど・・・。あっ、ダジャレですいません。
どう思いますか
0308デフォルトの名無しさんNGNG
LISPなんてマイナーな言語が考慮されるわけねーだろ!
0309デフォルトの名無しさんNGNG
マイナーな言語なんですか?
名前は良く聞きますが
0310デフォルトの名無しさんNGNG
>>308-309
いや、LISPはやっといた方がいいよ。
XML使うんならその前にLISPの本読んだ方がわかりやすいと思う。
0311デフォルトの名無しさんNGNG
XML表現
<い><ろ><は>匂えど</は></ろ></い>
lisp表現
(い(ろ(は 匂えど)))

XMLめんどくさい
0312デフォルトの名無しさんNGNG
つまりXMLは糞ってことですね?
0313デフォルトの名無しさんNGNG
(car '(い(ろ(は 匂えど))))
い
(caadr '(い(ろ(は 匂えど))))
ろ
(car (cadadr '(い(ろ(は 匂えど)))))
は
(cdr (cadadr '(い(ろ(は 匂えど)))))
(匂えど)
(cadr (cadadr '(い(ろ(は 匂えど)))))
匂えど

こういうのXMLだとどうなるんだろう
0314デフォルトの名無しさんNGNG
lisp ; XML
(car x) ; x.getTagName()
(cdr x) ; x.getChildNodes()
0315デフォルトの名無しさんNGNG
(cadr x) ; x.getFirstChild()
0316デフォルトの名無しさんNGNG
<い><ろ><は>匂えど</は></ろ></い>.getTagName()
い
ですか?>315
0317デフォルトの名無しさんNGNG
>>316
ごめん良く知らない。DOMで検索して
0318デフォルトの名無しさんNGNG
lispわかるなら、こういうの使えばいいかも
XMLTOOLS
http://www.graco.c.u-tokyo.ac.jp/~kamina/xmltools/
0319デフォルトの名無しさんNGNG
ありがとう。>318
でもおおきいですね。(ファイルが)
reader/writerだけ抜き出して使うことにします。
0320デフォルトの名無しさんNGNG
属性はどうするんだろう。
やっぱget/put使うのか。
0321デフォルトの名無しさんNGNG
get/putは symbolごとにしか使えないんじゃ...
0322デフォルトの名無しさんNGNG
>>321
となると
(tag (attr (name value) (name value) ...) contents...)
かな?
0323デフォルトの名無しさんNGNG
職業プログラマだけど、Scheme萌え〜!
ついでにSICPも一緒に萌え〜!!
0324デフォルトの名無しさんNGNG
処理系の大きさを考えれば、
自作言語はschemeで決まり。
0325デフォルトの名無しさんNGNG
>>324
小さくて済むから幸せだよ、という意味での発言だとすれば、
じゃあForth系は?という反論が来ると思われ。

使いたくはないけどなForth(藁
0326デフォルトの名無しさんNGNG
schemeって、もしかして無限相互再帰してもスタック消費しない?
(define (x n) (display 'x) (display n) (y (1+ n)))
(define (y n) (display 'y) (display n) (z (1+ n)))
(define (z n) (display 'z) (display n) (x (1+ n)))
(x 0)
x0y1z2x3y4z5x6y7z8x9y10z11x12y13z14x15y16z17x18y19z20...
0327デフォルトの名無しさんNGNG
>>326
インタプリタでは消費しない実装方法があるけど、
それを言語仕様で保障してるか不明。多分処理系依存でしょう。
今試しに、hobbitっていうscheme->cトランスレータ通したら
ただの関数呼出しになっていました。
(このトランスレータは自己末尾再帰やnamed-letとかならgotoに直せる)

SCM x(n)
SCM n;
{
display(x_symb,cur_output_port());
display(n,cur_output_port());
return y(apply(GLOBAL(nonum_prefix_1_plus_),n,listofnull));
}

SCM y(n)
SCM n;
{
display(y_symb,cur_output_port());
display(n,cur_output_port());
return z(apply(GLOBAL(nonum_prefix_1_plus_),n,listofnull));
}

SCM z(n)
SCM n;
{
display(z_symb,cur_output_port());
display(n,cur_output_port());
return x(apply(GLOBAL(nonum_prefix_1_plus_),n,listofnull));
}
0328デフォルトの名無しさんNGNG
letrecで試しても同じ結果
(define (xyz n)
  (letrec (
    (x (lambda (n) (display 'x) (display n) (y (1+ n))))
    (y (lambda (n) (display 'y) (display n) (z (1+ n))))
    (z (lambda (n) (display 'z) (display n) (x (1+ n))))
          )
    (x n)
  ))
0329デフォルトの名無しさんNGNG
SCM xyz(n)
SCM n;
{
  return xyz_fn1(n);
}

SCM xyz_fn3(n__6)
SCM n__6;
{
  display(z_symb,cur_output_port());
  display(n__6,cur_output_port());
  return xyz_fn1(apply(GLOBAL(nonum_prefix_1_plus_),n__6,listofnull));
}

SCM xyz_fn2(n__5)
SCM n__5;
{
  display(y_symb,cur_output_port());
  display(n__5,cur_output_port());
  return xyz_fn3(apply(GLOBAL(nonum_prefix_1_plus_),n__5,listofnull));
}

SCM xyz_fn1(n__4)
SCM n__4;
{
  display(x_symb,cur_output_port());
  display(n__4,cur_output_port());
  return xyz_fn2(apply(GLOBAL(nonum_prefix_1_plus_),n__4,listofnull));
}
0330デフォルトの名無しさんNGNG
確かにインタプリタだと止まらない。
0331デフォルトの名無しさんNGNG
Schemeを最近始めました。読むのはつらいですけど書くのは楽しいです。
Scheme で「モジュール」的なプログラミングをしたいときどうしますか。
つまり、複数の関数のみで共有する変数・関数を作りたいときです。
(Cでいうと、関数の外で定義されたstatic変数・static関数みたいなやつ)
「プログラミング言語Scheme」に書かれていた方法で行くと

(define set-var #f)
(define get-var #f)
(let ((local-var #f))
  (define (set-var-1 x) (set! local-var x))
  (define (get-var-1) local-var)
  (set! set-var set-var-1)
  (set! get-var get-var-1) )

ちょっと面倒ですけど、これでlocal-varは外からはアクセスできないように
できますね。
実際に皆さんはこういうふうに書いているのでしょうか。
0332デフォルトの名無しさんNGNG
> 327 名前:デフォルトの名無しさん投稿日:2001/06/19(火) 04:25
> >>326
> インタプリタでは消費しない実装方法があるけど、
> それを言語仕様で保障してるか不明。多分処理系依存でしょう。

保証してるよ。R^5RSの「Proper tail recursion」の節を読むべし。
0333デフォルトの名無しさんNGNG
>>331
その方法でも良いんだけど、
変数の直接変更を嫌うなら、メッセージパッシングという方法があるよ。
メッセージを処理するクロージャを返す関数を作るんだけど。
これを使うと、必ずメッセージ経由でデータが処理される事が保障される。
例えば下は文字列のポインタを表現するオブジェクト
メッセージに使うアトムは何でも良いけど、ここではシンボルだけを使ってます。
(define (make-strptr s)
  (let ((pos 0)) ;s のoffset
    (lambda (m)
      (case m
        ((++) (set! pos (+ pos 1)) #t) ; ポインタを1文字進める
        ((--) (set! pos (- pos 1)) #t) ; ポインタを1文字戻す
        ((refch) (string-ref s pos)) ;文字の参照
        ((setch) (lambda (ch) (string-set! s pos ch) #t)) ;文字の設定
        ((reset) (set! pos 0)) ;位置のリセット
        ((rest) (substring s pos (string-length s))) ;参照位置以降の文字列
        (else #f)
      ))))

;make-strptrは文字列"abcd"を管理するポインタを作る
(define strptr (make-strptr "abcd"))
=>strptr
(strptr '++)
=>#t
(strptr 'refch)
=>#\b
((strptr 'setch) #\x)
=>#t
(strptr 'rest)
=>"xcd"
0334デフォルトの名無しさんNGNG
(retrec ((this (lambda (m) 〜
 ((++) (set! pos (+ pos 1)) this)
 〜))
 this
)
副作用が目的で、戻り値が必用無いメッセージの場合、
上の様にthis(メッセージ処理closure)を返す様にすれば、
(strptr 'rest)
=>"abcde"
((strptr '++) 'refch) ;1文字進めて今注目してる文字を返す。
=>#\b
の様に書ける。
0335デフォルトの名無しさんNGNG
>>331

GOOPS
http://www.gnu.org/software/goops/goops.html
0336デフォルトの名無しさんNGNG
SICPにデータ主導プログラミングの方法が載ってるけど
あれでは駄目ですか?>331
0337331NGNG
>>333,334
そのような手法もあるのですね。良く分かりました。
ありがとうございました。
>>335
ちょっと敷居が高そう。でも努力してみます。ありがとうございました。
>>336
SICP?調べたら有名な教科書なんですね。
恥ずかしいことに名前を聞いたこともありませんでした。
さっそく買いに行きます。ありがとうございました。
0338デフォルトの名無しさんNGNG
(define generic-function-table
;優先度:高↑
`(
;書式(関数名 検査する型の並び 実際に呼び出す関数)
(- (,number?) ,-)
(+ (,number?) ,+)
(+ (,string?) ,string-append)
  ;・・・
)
;優先度:低↓
)

(call-generic-function '+ '(1 2 3)) ;引数が全て数値型なので+が呼ばれる
=>6
(call-generic-function '+ '("a" "b" "c")) ;引数が全て文字列型なのでstring-appendが呼ばれる
=>"abc"

引数の型によって呼び出す関数を切り替える総称関数みたいなのは
>>335の様な拡張ライブラリ使わなくてもできる。
CLOSみたいなクラスもこれにクラス用の述語(〜?)を定義すれば書けなくも無い。
マクロと併用すれば、型が限定されてるとき直接それ専用の関数を埋め込む事
もできそう。
(多分>>335のライブラリは型判定の効率を上げるためにコアをCで書き直したものだと思うけど。)
0339デフォルトの名無しさんNGNG
>>338
>マクロと併用すれば、型が限定されてるとき直接それ専用の関数を埋め込む事
そのやり方だと、埋め込めるのは引数が定数の時だけだよ。
他(変数やリスト)はどうしても動的判定になる。(CLOSも同じ)
(apply-generic-funcrion + (<a-class> a) 1 2)
(apply-generic-funcrionはマクロとする)
とか、型を明示的に指定すればマクロ内で埋め込み処理可能かもしれないけど。
0340デフォルトの名無しさんNGNG
Lisp の中をのぞいてみると...

新人「あ!先輩!何かS式がやってきましたよ!」
先輩「先頭にアポストロフィーついてっか?」
新人「はい、ついてます!」
先輩「よし、だったらそのままピーコしてエコーエリアに流せや」
新人「え!そんなんでいいんですか?」
先輩「おうよ、頭にアポストロフィーがついてるやつは、そのまま流せ。楽でえーわ」
新人「こんなんで給料もらっていいのかなぁ...あ!先輩!こんどは頭にアポストロフィーがついてないやつがきました!」
先輩「なに...?!」
0341デフォルトの名無しさんNGNG
「前回までのあらすじ」
-- 大学卒業後、知人の紹介で Lisp で働くことになった新人 K 君。
少々口は悪いが気はやさしい先輩にめぐまれ、新人研修をこなす毎日だが.... --

先輩「そのS式の1番目のアトム確認しろや」
新人「はい!えーと,,, + って書いてますね」
先輩「プラスか...(ニヤソ)またきやがったか」
新人「よくくるんですか?」
先輩「まあな...おい、おまえ、大至急資料室いって、+のデーター集めてこいや」
新人「了解しました!」

いきおい良く廊下に飛び出していく新人君。
しかし、彼に恐ろしい運命が待ちうけているとは誰が想像できただろうか....

<第2部に続く>
0342デフォルトの名無しさんNGNG
>>340-341
新人 :read write その他雑用
先輩 :eval apply
資料室 :環境
ですか?

うちの環境だと起動時の初期化だけで
新人、先輩とも8万回(単純計算)は呼びだし食らってます。
大変だなあ・・。
0343デフォルトの名無しさんNGNG
Visual LISPとか無いのかねえ。
0344デフォルトの名無しさんNGNG
>>343
VisualC++みたいなのか?それともVB/Delphiの方か?
どのみちGUI作ったりしない限りは、名前補完と括弧対応付け
できるエディタぐらいしか用無いんだけど。
0345デフォルトの名無しさんNGNG
Smalltalk-80 のイメージみたいに、Lisp による Lisp のための
ウィンドウシステムつき Lisp ってのはフリーでは無いのかなあ。
0346デフォルトの名無しさんNGNG
がいしゅつだがSTkじゃだめか?
さいきんはGuile-Gtkとかもあるが…
ST80ぐらいまで統合されているのは見たことない。けど、むかしのLispマシンってのはそうだったんでしょ?
0347デフォルトの名無しさんNGNG
「リスト遊び」本にしばしばリストが繋がっているさまを描いた絵が
出てくるんだけど、ソースからあの絵を起こすんじゃなく逆に
あーいう絵「を」ぐりぐり動かすことでプログラムを「書く(描く?)」
ってのはLispとかでは望めそうですか?

特にLisp系は仕掛けが単純化されてるんで相性が良いと思うんだけど、
CARとかをマウスでつまんで他のCellにDropすると
参照を示す線がびゅびゅっと出て…みたいなのって
簡易プログラミングとして楽しいと思うのだが、どう?

掃除機の電源ケーブル引きまわしみたいなイメージだな(藁

頼むから、そういうのを学研の付録としてつけてくれぃ。
子供がみんな喜んでいじくりまわすぞ。
0348デフォルトの名無しさんNGNG
>>345
やっぱり電通大の竹内郁雄氏に弟子入りするしかないのでわ。
相変わらずハードからLisp作っているそうだし。
0349デフォルトの名無しさんNGNG
(substring "The quick brown fox jumped." 16 19)

これを評価すると
"fox"
と結果が返ってきます。次に

(substring "The quick brown fox jumped." 16 18)

これを評価すると
"fo"
になります。
ということは、
16 → f
17 → ?
18 → o

となるのでしょうか。
0350デフォルトの名無しさんNGNG
自己解決しました。
3番目の引数は、抜き出したい文字列のひとつ右側を指定する、ということです。
0351デフォルトの名無しさんNGNG
global環境で
(define *toplevel* '())
(call/cc (lambda (cont)
(set! *toplevel* cont)))

を定義したあと、任意の階層/場所で
(*toplevel*)
これって合法ですよね?
ところで、こういう風に返った時は、
call-with-i/o関係の後始末はしてくれるものですか?
0352デフォルトの名無しさんNGNG
> 351 名前:デフォルトの名無しさん投稿日:2001/06/26(火) 00:52
…中略…
> を定義したあと、任意の階層/場所で
> (*toplevel*)
> これって合法ですよね?

合法。

> ところで、こういう風に返った時は、
> call-with-i/o関係の後始末はしてくれるものですか?

GCが回収するか陽に閉じるまでは、開かれたportは閉じてはいけないことになっ
ている。R^5RSのPortsの節を読むべし。
0353デフォルトの名無しさんNGNG
ありがとうございます。>>352
ということは、やっぱりi/o-portとかを自動的に(確実に)破棄
したい場合CommonLispでいうunwind-protectの様な機構を自分で
作っておく必要があるみたいですね。
0354デフォルトの名無しさんNGNG
今月のCマガ見たらschemeの記事が載ってた。(コラムで2ページだけ。)
やっぱGuileとかの影響?
記事書いてたのがきだあきら氏ってのもあるだろうけど。
他のページにrubyの末尾再帰の話題が出てたのが興味深い。
rubyって末尾再帰展開やってくれないんだね。
0355デフォルトの名無しさんNGNG
schemeの継続を使ってマルチスレッドモドキを作れるって
どこかで聞いたんですが、これは協調型スレッドの事ですか?
0356デフォルトの名無しさんNGNG
>>355
多分そうです。
どう考えてもプリエンティブにはならないと思います。
OS側で用意されてる割り込みとか、特殊な物使えば出来そうですが。
(OSネイティブでスレッド機構があったらそれ使った方が良い)
継続でやる場合、恐らくVBのDoEventみたいな関数を用意して、
自前で切り替えタイミングを発行をする様な形になる筈です。
実装するとしたら、おそらくこんな感じです。

(継続振り分け関数)

↓起動   ↑各スレッド内でDoEvent関数を呼ぶと振り分け関数に継続が渡る

(スレッド関数1) (スレッド関数2) (スレッド関数3)
0357デフォルトの名無しさんNGNG
恐らく継続でスレッドを作る利点は、環境依存しない事ですが、
継続の切り替え効率が悪い処理系があると思います。
例えば、継続をハードウェアスタックで管理している処理系は
切り替える度にスタックのコピーが発生するので遅くなります。
ヒープで管理している処理系ならば瞬時に切り替わります。
(ただし、後者は元々全体的に遅い。)
0358デフォルトの名無しさんNGNG
あと、排他制御が必要無いので、タイミングによる不具合が
発生しないというのも利点だと思います。
(この切り替え機構を「スレッド」と呼んでいいの疑問ですが。)
0359デフォルトの名無しさんNGNG
その方法って、どこかのスレッドがI/O待機関係とかでブロックしたら、全体が止まってしまうんじゃない?>358
細切れにするか、非同期I/OにしてWaitForObjectとかで待てばいいんだろうけど。
GUI作るとき何も考えずにメッセージループを複数作れる、ってのはいいかもね。
0360デフォルトの名無しさんNGNG
コルーチン?
0361デフォルトの名無しさんNGNG
コルーチンの一種なんだけど、Smalltalk の fork. とか Mac (w
や昔の Windows のナニとかも含めて、協調型マルチタスクと呼ばれる
ことが多いと思う。コルーチンっていう言い方は、複数の「関連した」
処理が continuation で協調動作してひとつのタスクを遂行する、
って場面でより多く用いられるんじゃないかな。
0362デフォルトの名無しさんNGNG
Lisp を学ぶことは、最初の道が急な坂であるような丘を登るようなものである。あなたが現在登っているのはもっとも急な部分である。先に進むに従って、より楽に進めるようになるはずだ。

↑とか書いてあるが、先に進めば進むほど、難しくなってきたぞゴルァうそつくなや
0363デフォルトの名無しさんNGNG
>>362
どのへんが難しい?
0364デフォルトの名無しさんNGNG
初心者だと最初に躓きそうなのはdot対とか
0365デフォルトの名無しさんNGNG
IO関係の関数を全部定義しなおして wrapperかけてやって..
面倒くさいけど、そういうのもできるな>>359

CMU CommonLispとかは、command lineの裏で走ってる
ものとかあったな.. あれはなんだったんだろ。
よくわからず使っていた俺。
0366デフォルトの名無しさんNGNG
こんな感じで書ければ既存コードに(do-event h)埋め込むだけで使えそう。
(define t (make-thread-object))
;thread closureの登録
((t 'beginthread) 'id1 (lambda (h) 〜(do-event h)〜 (endthread h)))
=>id1
((t 'beginthread) 'id2 (lambda (h) 〜(do-event h)〜 (endthread h)))
=>id2
((t 'beginthread) 'id3 (lambda (h) 〜(do-event h)〜 (endthread h)))
=>id3
;thread id1〜3の振り分けの実行
(t 'run)
---------
tは振り分け
hは各threadのuniqなハンドル

suspend/resumeも作れば結構実用性あるかもね。
0367デフォルトの名無しさんNGNG
メッセージパッシングを用いない場合はこんな感じ
(runthread (lambda (t)
 ;thread closureの登録
 (beginthread t 'id1 (lambda (h) 〜(do-event h)〜 ))
 (beginthread t 'id2 (lambda (h) 〜(do-event h)〜 ))
 (beginthread t 'id3 (lambda (h) 〜(do-event h)〜 ))
))
最後のendthreadは自動で呼び出す様にすれば必要ないね。
作るのはちょっとめんどっちいかな?
0368デフォルトの名無しさんNGNG
Lisp って C で作られてるの?
0369デフォルトの名無しさんNGNG
>368
lisp自身は当然として、
アセンブラとかjavaとかawkとかもあるよ
質はまちまち
0370デフォルトの名無しさんNGNG
それじゃあ、Lisp を真に理解するためには、まず C を勉強しなければならないの?
でも、C のコード書くためにエディターが必要で、Emacs 使うなら、Emacs Lisp の勉強が必要で、Lisp の理解のために C の知識が必要で、......
0371デフォルトの名無しさんNGNG
Lispを理解したいならLispを理解すればいい。
0372デフォルトの名無しさんNGNG
>>370
あんたの理屈だと、Cを勉強するためにはアセンブラが
必要で、アセンブラのためにはハードの知識や
デジタル回路理論、量子力学までぜんぶ必要になるんじゃないか?
0373デフォルトの名無しさんNGNG
Lispのエッセンスを理解するには
まずS式をconsセルのリストとみなすこと.
そうすれば様々な操作が自然に見える.
あとはS式の評価規則だけ.
0374デフォルトの名無しさんNGNG
確かにそうですよねぇ...
もし、
「日本語はもともと中国語からできてるのだから、本当に日本語を理解したければ、まず中国語を学ぶべきだ」
という主張があったらかなり変ですしね。

言語学者がそのようにいうならいいかもしれませんが、0才児にそんなこといっても意味ないですしね。
0375デフォルトの名無しさんNGNG
ただ、Lispを使ってても計算機のアーキテクチャに関する
知識はいずれ必要になってくるが、それはOfficeを使うのに
PCIカードやドライバのインストールについて知らなきゃいけない
のと同じよーなもんだ(すこしちがうかな)。
0376デフォルトの名無しさんNGNG
「Lispを理解したい」ってだけなら>>371が言った、
>Lispを理解したいならLispを理解すればいい。
で十分だよ

ただしlisp処理系を作りたいのであれば、それの基盤言語を何にするかに
よってその基盤言語の理解が必要。
lispでlispを作るのであれば理解するのはlispだけでいい。
実行効率を上げる必要があれば基盤言語に効率の良さそうな言語を選べばよい。
0377デフォルトの名無しさんNGNG
で、実行効率と汎用性の点などで考えると、
基盤言語にCやアセンブラの組み合わせを使う場合が多い。
0378デフォルトの名無しさんNGNG
これはperlやpython、rubyやC、pascalなど、
他の言語にも言えること。
perlを使うのにperlの実装を知る必要は無いでしょ。
0379デフォルトの名無しさんNGNG
ただしlispは構造が単純で、自分で手軽に作成する事ができるから、
実装を理解するハードルは比較的低い。
現にlispのほとんどの教科書にはlispをlisp自身で作成/拡張する、
という章があったりする。
0380デフォルトの名無しさんNGNG
>>363
この練習問題が難しいです。
でも、答えは書かないで下さい。
自分で考えます。

「現在の fill-column の値が関数に渡される引数よりも大きいかどうか判定し、もしそうなら適当なメッセージを表示するような関数を書きなさい。 」
0381デフォルトの名無しさんNGNG
>>380

       ∧∧
       ( ゚∀゚) あーできたー
       ヽ|〃
 ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄

(defun hantei (number)
"setumei"
(interactive "p")
(if (> fill-column number)
(message "fill-column is bigger than the entered number!")))
0382デフォルトの名無しさんNGNG
昔(386とか486時代)lispインタプリタ上で動くlispって作ったけど、かなり遅かった。
バイトコードコンパイラでも作っておけば、もうちょっと改善されたかも
しれないけど。(でもバイトコードの設計って大変)
今はインタプリタだけでもそこそこの速さで動くからありがたい。
0383デフォルトの名無しさんNGNG
ものすごい遅レスだけど、
>>29
itemをclosureにすれば表示させても問題無いよ。
(define (make-item obj next prev)
 (lambda (m)
  (case m ((next) next)
      ((prev) prev)
      ((obj) obj)
      ((set-next!) (lambda (p) (set! next p)))
      ((set-prev!) (lambda (p) (set! prev p)))
      ((set-obj!) (lambda (p) (set! obj p)))
  ) ))
0384デフォルトの名無しさんNGNG
あと、メッセージパッシンングだけど、
よく使うメッセージについては常にclosureを返すようにすれば、
そのclosureをdefineすることでメッセージ探索の数を減らす事ができるよ。

>>383のmake-itemの例なら、
;メッセージパッシングclosureを作成
(define item (make-item 'obj 'next 'prev))
;メッセージ処理後のclosureを保存
(define item-set-next! (item 'set-next!))
(define item-set-prev! (item 'set-prev!))
;直接closureを呼ぶ
(item-set-next! 'next) ;itemのnextに影響
(item-set-next! 'prev) ;itemのprevに影響
0385デフォルトの名無しさんNGNG
>>383の双方向リストの要素の様に、沢山生成される
可能性がある場合、closureにすると、環境フレームを1つ
作成する事になるわけで、例えば環境フレームを
(変数名 . 値)のペアの連想リストで保持する処理系だと、
((obj .var1) (next .var2) (prev .var3))
こうなって、consセルが6個必要になる。
>>29の方法そのままでは
(var1 var2 . var3)
consセルは2つで済む。
引数を
(make-item obj next prev) -> (make-item obj-next-prev)
という風にまとめても、
((obj-next-prev .(var1 var2 . var3)))
consセルは4つ必要。
どちらにしろ倍にはなるので、あまり小さい単位ではclosure化は
しない方が良いと思います。(処理系に依るでしょうけど)
0386デフォルトの名無しさんNGNG
>>385
じゃあ、内部では(cons obj (cons next prev))で処理して、
外部に出す時はiterater(pointer)の機能を持った
closureでラップして返す様にすればよいかな?
0387デフォルトの名無しさんNGNG
>>351
デストラクタのclosureのstackを作っておいて、
あとで一気に実行すれば、安全な破棄ができると思う。
(define (closure-stack) (display "bottom"))
(define (closure-push closure)
 (let ((old-closure-stack closure-stack))
  (set! closure-stack
   (lambda ()
    (closure)
    (set! closure-stack old-closure-stack)
    (old-closure-stack) ))))
;デストラクタ
(define (test n) (lambda () (display n)(newline)))

;デストラクタの登録
(closure-push (test 1))
(closure-push (test 2))
(closure-push (test 3))
(closure-stack)
3
2
1
bottom
;もう一度実行しても123は呼び出されない。
(closure-stack)
bottom
0388デフォルトの名無しさんNGNG
(closure-stack)をerrorの時一緒に呼び出すって意味ね
0389デフォルトの名無しさんNGNG
>>353
なんだ、unwind-protect知ってる人なのね・・・
0390デフォルトの名無しさんNGNG
( ゚∀゚)
Error: Unbounded variable ゚∀゚
0391デフォルトの名無しさんNGNG
schemeにもlispのpackageがほしい
0392デフォルトの名無しさんNGNG
read-eval-loopを細工すれば出来るかもしれないが、
環境依存
0393デフォルトの名無しさんNGNG
winでschemeやりたいんだけど、どれがいいの?

Lisp初心者。Common Lisp, Emacs Lispなどは名前を知っているという程度。
C,Java,Perlなどは初心者++。

ちなみに、
ChezEdit
http://www5a.biglobe.ne.jp/~sasagawa/MLEdit/Scheme/index.html
を使ったところ、括弧がうざいというのは幻想なんだなと思いました。
(まだまだ短いプログラムしか書いてないからかも?)

で、ChezEditを使っていて思ったのは、前置式うざい、ということ。
Lispの勉強をまともにやる前(本のソースを眺めてたころ)は、「あー括弧うぜー」
でした。しかし、やり始めると、括弧より前置式のほうがはるかにうざく感じます。
慣れてないというのもあると思います。

しかし、エディタのモードでなんとかなるのでは?とも思いました。

例えば、
(a + b) * c
を前置式で入力するとき、
(+ a b)
って入力してから、「あ”、*あった・・・。欝だ」みたいな感じです。
このとき、カーソル左を連打して、忘れていたのを挿入してます。
(↑ここが、エディタのモードを使えばなんとかなるかな?と思った)
(例えば、M-x chotto-modoru(仮))
(Emacsに(たぶん)schemeモードとかあると思うけど)
Winではxyzzy使ってるし・・・。


みなさんは前置式の入力はどうやってますか?
0394デフォルトの名無しさんNGNG
Emacsだと M-C-b ( * SPC M-C-f SPC c ) だね
0395デフォルトの名無しさんNGNG
>>393
WinやUNIXならSCM(Guile)/STK/ELK/DrScheme/RScheme/MITSchemeなど、
フリーで色々選択肢あると思います。
SCMが速いという話をどこかで読んだ事がありますが、
実際に計った事はないのでなんとも言えません。
bashのコマンドラインに慣れているなら、readlineが組み込まれているGuileとか。
日本人が現在進行形で作って公開してるやつはgaucheやrhizome/piというのがあります。
これらは日本語も問題無く扱えると思います。
(私は公開してませんが、自作のやつ使ってます。)
0396デフォルトの名無しさんNGNG
>>393
>みなさんは前置式の入力はどうやってますか?

中置式を展開するフィルター使うって手は・・?

(infix-expand b * q + a * q + a * p)
=>(+ (* b q) (* a q) (* a p))

こういうのは自分で作るしかないけど、便利ですよ。
今持ってるやつは、リスト→リスト変換なんで、セパレータに
空白入れる必要があるから不便です。
文字列→リストにすれば見やすいかと思います。

(infix-string-expand "b*q+a*q+a*p")
=>(+ (* b q) (* a q) (* a p))

Guileという処理系にこういう中置文字列→前置リストの
変換ライブラリがある様です。
0397デフォルトの名無しさんNGNG
emacsならバッファの内容をS式と見なして評価できるんじゃないの?>393
0398デフォルトの名無しさんNGNG
lisp使うならエディタをemacsやxyzzyに乗り換えた方がいいでしょうか?
0399デフォルトの名無しさんNGNG
補完、ヒストリ付きの一行エディタあれば十分な気もする
0400デフォルトの名無しさんNGNG
前置式つーか、lispに演算子は無いからねえ。>>393
全部関数呼出しと考えればいいんじゃないの?
演算子として使いたいなら、>>396 みたいに式解析させた方が後々楽だと思うよ。
0401デフォルトの名無しさんNGNG
cygwin版(かwinで動く)lispってないんですか?
エディタのおまけではなくって純粋な処理系が欲しいです
0402デフォルトの名無しさんNGNG
沢山あると思うんだけど。
検索してみれ>401
0403デフォルトの名無しさんNGNG
CommonLisp処理系の中でメジャーなのってなんだろ?
漢字対応してる処理系って事だとかなり限られてくると思うんだけど。
xyzzyは駄目なの?>401
0404デフォルトの名無しさんNGNG
研究用では Allegro CL がよく使われてる。
0405デフォルトの名無しさんNGNG
たかいよ>ACL
それないの性能なんだろうけど。
学割効くとなんぼかましになるのかな
0406デフォルトの名無しさんNGNG
progn てなんて発音するの?
ぷろぐん?
0407デフォルトの名無しさんNGNG
prog1 ぷろぐいち ぷろぐわん
progn ぷろぐえぬ
読み方の根拠は、元々n番めの評価結果を返すって意味だろうから。
prog1は最初の評価結果。
0408デフォルトの名無しさんNGNG
n番め、つーのはシーケンスの最後って意味ね。
programよりsequenceって名前にすればわかりやすかったん
じゃないかと思う。
Schemeのbeginも用途の割に変な名前。
恐らくPascal言語辺りのbegin 〜 endから取ったんだろうけど、
そもそもschemeにはendが無いし。
ネーミングセンスよくないよね。
0409デフォルトの名無しさんNGNG
元々lambda/let/condなどはbeginを含んでるから、
beginを直接コード上に置くことってあんまりないからいいけど。
破壊操作系に!、述語系に?を付けるって習慣はよい事だと思う。>scheme
規則を守ってるかどうかはともかく。
0410デフォルトの名無しさんNGNG
rplaca
rplacd
とかもいまいち。これはschemeだと
set-car!
set-cdr!
に対応する。
0411デフォルトの名無しさんNGNG
(chubo? a)
0412デフォルトの名無しさんNGNG
(chubo? 411)
0413デフォルトの名無しさんNGNG
#t
0414デフォルトの名無しさんNGNG
そもそもセンスの悪さはcar/cdrが元凶だと思われ。>408
(caddr '(a b c))
=>c
とか書けて便利なんだけど。
CommonLispでは、代わりにfirst/restがあるけど、
これは使い勝手悪し。(schemeでは消えた)
0415デフォルトの名無しさんNGNG
>>409
nullやatomは歴史的経緯からか知らないけどpが無いのが納得いかない。
schemeでは それぞれnull? atom?
(atom?ってあったっけ)
実際は、これらを直接使って書いていく事はあんまり無いから良いかもしれないけど。
0416デフォルトの名無しさんNGNG
(eq? >>411 >>412)
0417デフォルトの名無しさんNGNG
>>391
packageというか、
環境のフレームを持ち回る、というのなら可能。
でもフレームの構造を知ってないと駄目だから、
やっぱり処理系依存という事になると思う。
(Schemeって環境の内部構造まで規定してないよね?)
0418デフォルトの名無しさんNGNG
例えば、うちの処理系なら
(car (current-environment))
で現在のローカルフレームだけ取り出せる。
現在いる所がローカルフレームじゃ無ければグローバルフレーム。
(set! c-frame (append a-frame b-frame (interaction-environment)))
とでもして、この環境c-frameをevalすれば、
(eval expression c-frame)
expressionでの定義はc-frameに作成される。
これは単に処理系がこういう事するのを許しているからであって、
schemeの標準仕様には無いと思う。
これを踏まえた上てread-eval-printを書き換えれば、
packageのエミュレートも可能だと思う。
0419デフォルトの名無しさんNGNG
フレームの保存
(define (make-package env) (lambda () env))
(define a-package #f)
(let () ;ローカルフレームのためのlet
(load "a.scm" (current-environment))
(set! a-package (make-package (car (current-environment))))
)
loadに現在の環境(letのローカルフレーム)を渡す。
環境をmake-packageで挟んでclosureにしているのは、
(current-environment)をそのまま表示した時に起きる再帰的な
不都合を、回避するため。
これで
(a-package)
とすれば、いつでもローカルフレームが得られる。
このローカルフレームを使いたい場合、
(eval expression (cons (a-package) (interaction-environment)))
とでもすれば、expression内でa-packageの定義がグローバル環境より優先的に参照される。
0420デフォルトの名無しさんNGNG
ここまでをテンプレート化すると、
(define (make-package env) (lambda () env))
(define (package-expand name fn)
 (let ((pkg-name (string->symbol (string-append (symbol->string name) "-package")) ))
  `(begin
   (define ,pkg-name #f)
   (let ()
    (load ,fn (current-environment))
    (set! ,pkg-name (make-package (car (current-environment))))
   )) ))
(define-macro (package name fn) (package-expand name fn))

用法
(package a "a.scm")
=>#<closure>;a-package closureが生成される。

;;read-eval-print-loopにa-packageを適用する。
(read-eval-print-loop (cons (a-package) (interaction-environment)))
>(a-func) ;a.scmで定義された関数を使う。
=>ok
>(exit) ;ローカルのread-eval-print-loopを抜ける

(a-func) ;グローバル環境で使おうとしてもエラーになる
=>Error:Unbound symbol 'a-func'
0421デフォルトの名無しさんNGNG
>>420はCommonLispのpackage機構には程遠い実装ですが、本質的には同じ事です。
(あっちはpackage間の移動とか、package:nameでアクセスできたりできますが。)
グローバル環境に沢山定義を溜めておくと、検索に時間が掛かったり、
名前の競合が発生したりと、良いことがあまりないので、
こういった機構は標準で存在すると便利なんだけど。
(せめて環境の内部構造までを標準化してくれるとありがたい。)
0422デフォルトの名無しさんNGNG
package/use-package/require
辺りが初めから付いてる処理系はよく見かける。
CommonLispのやつと互換性あるのかは知らないけど。
0423デフォルトの名無しさんNGNG
420見て思ったけど、beginって環境作んないんだね。
(if (undefined? hoge) (begin
(define hoge #t)
) (begin
(set! hoge #f)
))
グローバルに対して条件実行できるじゃん。
0424教えて君みたいで嫌だけどNGNG
kispっていっぱいあって訳わからないんだけれど、
lispとschemaって違うの?
とりあえず有用なのはどれ?
覚えるには何で覚えるのがベスト?
0425デフォルトの名無しさんNGNG
>>424
なんでもいいんじゃないの?
このスレはScheme中心みたいだけど。確かに今学習すんならSchemeはお勧め。
(Schemeは別に学習専用ってわけじゃないからね。)
GNUの標準スクリプトになりつつある様だし。
何からやるにしても、ある程度覚えればほかのlispも使える様になるよ。
0426デフォルトの名無しさんNGNG
>>424
メジャー度でいうと、
EmacsLisp > CommonLisp > Scheme > その他lisp方言沢山
って感じだろうけど、少なくともEmacsLispは学習向きじゃないと思う。
非標準な関数だらけ。エディタと連携して使う分にはいい。
CommonLispは仕様が大きすぎるので、こればっかりやってると挫折しそう。
Schemeは確かに学習向きだけど、それでも既に他のlispを触わっている
事を前提にした説明が多い。(規格書がちょうどそんな感じ。)
多分、SchemeとCommonLispを交互にやっていくのが面白いと思う。

あとネットに転がっている、個人で公開してる様なマイナーな
lisp方言もたまに触わってみると感じが掴めると思う。
変なのに当たらなければ、こっちから入るのも良いかも。
0427デフォルトの名無しさんNGNG
>>426
ウゥ俺は elisp しか判らないよ。
一度はちゃんとした lisp を勉強したいとはつねづね思っているんだけど。
0428デフォルトの名無しさんNGNG
schemeがいいよ。
末尾再帰、継続の存在は知っといた方がいい。
0429デフォルトの名無しさんNGNG
どうして、CommonLispとか、Schemeとかってはやらないのですか?
0430デフォルトの名無しさんNGNG
見た目が怖すぎるから、か?(w>>429
機能的には流行のperl,ruby,python,java辺りとかと比べても、
引けはとらないとは思う。
実行速度も下手なスクリプト系言語より速いし。
lispの機能は他の言語に吸収されつつあるみたいだけど、それでも
オリジナルの貫禄はまだ保たれていると思う。
例えば、perlにもあるevalとかは、字句解析器通す必要ないから、
lispが圧倒的に速い。(意味も多少異なる。)
0431デフォルトの名無しさんNGNG
人気が無い理由は、いくつか考えられるが、
演算子が無く、すべて関数記述(前置記法)で書かせるのが原因の一つ。
演算子として中置記法を処理するパーサーは簡単に書けるけど、
始めから用意されているわけではないし。
それと、何をするにも括弧で囲む必要がある。
セパレータは空白なので、くっつけて書くことができない。
0432デフォルトの名無しさんNGNG
>>424
学習用には、非常にコンパクトなislispを使用しました。
http://www.okilab.com/islisp/
言語としては最低限ではあるのですが、
どのlispにでも応用が利きそうな言語仕様なので、いいと思います。
0433デフォルトの名無しさんNGNG
elispも別にそれほど人気があるわけでは無い。
emacs信者が多いのは、ほとんどはエディタとしての価値が高いからでしょ。
確かにemacs==elispだけど、eispを主に使ってる人はあんまりいないみたいだし。
0434デフォルトの名無しさんNGNG
lisperは、最終的に自分用のlispを作りたがる傾向にある。
これも一般向けしない理由。
実装コストがあまりかからず、機能拡張が他の言語に比べて易しい。
0435Perl信者NGNG
>>429
このスレみて最近Schemeはじめました。
括弧や前置記法は個人的にはまったく抵抗ありません。

手を出しづらいのは、具体的に何ができるか、そのためにどう書くか、
という身近というか、下世話な情報が目立たないからだと思うのですが…。
Schemeの解説って、大抵Schemeの意義とか概念とか、難しい話が最初に長々とあって、
とにかく手をだしてみたいんだ! って人にはつらいかな、と。
本はまだ買ってないのでどうだかわかりませんが。
0436デフォルトの名無しさんNGNG
>>434
自分用のlispと言えば、
自作のschemeにdllアクセス機能付けて使ってるけど、
Windowコールバックとかにclosure置けるようにしたので楽。
call-with-なんたらと感覚が一緒。
やっぱsoやdllは見えた方が良い。
0437デフォルトの名無しさんNGNG

Tcp/Ip Addressing : Designing and Optimizing Your Ip Addressing Scheme (2nd Edition)
http://www.amazon.com/exec/obidos/ASIN/0122950216/103-5588829-5276648

こーゆーのもあるみたい。
0438デフォルトの名無しさんNGNG
>>435
lisp系は基本的にi/o関係が弱いです。
S式に直してなんぼの世界なので。
実用的と言われる処理系には、その辺の弱い部分を吸収する
ライブラリがあるので、それで補います。
perlを知ってるなら、まず言語がどうのというより、
似た環境(socket/文字列処理/正規表現辺りなど)
が揃ってる処理系を使ってみては?
0439デフォルトの名無しさんNGNG
うーん。みんなひっそりと個人用のプログラムに使っているんだろうね。
>>92 には消極的なレスしかつかなかったし。
ここに書込みされている方々がどんな用途にLisp/Schemeを使っているか
ぜひ知りたいです。
0440デフォルトの名無しさんNGNG
>>437
このSchemeは体系という意味の名詞だろ。
0441デフォルトの名無しさんNGNG
>>436
callbackの中でcall/cc呼ばれたときはどうしてる?
0442デフォルトの名無しさんNGNG
>>439
自作schemeなんであんまり参考にならないかもしれないけど、
言語処理(構文解析、トランスレータ)
GUIとかのプロトタイプ
socket通信
HTML出力とかのバッチ処理
文字列処理(+正規表現拡張)
その他実験、雑用(bignumや分数も使えるんで、電卓代わりとか。)
速度を除いて、Cとほぼ同じ事(特にポインタ回り)ができる様に
ライブラリを拡張してるから、使い勝手は悪くない。
インタプリタとしての利点がほとんど。
処理系の大きさはwindowsのexeにすると100kbぐらい。
0443デフォルトの名無しさんNGNG
>>441
エラーとかで復帰させる場合はlongjmpします。
復帰の必要が無いならcallback上で継続を切り替えます。
0444デフォルトの名無しさんNGNG
継続を切り替えた後もcallbackのスタックは存在します。
なので、後で必ずcallbackの継続へ戻らなければまずいです。
(もしくは、どこかでlongjmpさせる機会を作る。)
よって、callback上での継続切り替えは結構制限が掛かります。
これは仕方ないかな?と思ってます。
0445デフォルトの名無しさんNGNG
SCMとかはハードウェアスタックを直接切り替える様なので、
こういう場合では有利ですね。
0446デフォルトの名無しさんNGNG
message loopで切り替えるなら問題ない
0447デフォルトの名無しさんNGNG
ある問題を本質的に理解したいと思うとき、
SchemeとかMLなんかで解いてみると確実に
理解が深まるという印象がありますね。

実用システムにLISP/Schemeが使われない
理由は、開発環境と実行環境が一体化して
おり、実行可能ファイルだけを配布するの
に向かないからではないでしょうか。
Dylanの解説本にそういうことが書いてあ
りました。

Cにトランスレートしてコンパイルすれば
いいって言っても、開発時と異なる環境で
動作させて、本当に動作が変化しないとい
う保証はないわけですし。
0448デフォルトの名無しさんNGNG
>>447
そういえばexe化は考えたこと無かったなあ。
lisp/scheme->cにするツールはいくつか有りますが、
質はまちまちみたいです。
(相互末尾再帰をちゃんと展開しないscheme->cトランスレータは最近見ました。)
ソース見せたく無いってだけなら、vbみたくschemeランタイムと
バイトコードモジュールの込みで配布するって手段が簡単そうですが。
(逆アセには弱そう)
0449デフォルトの名無しさんNGNG
closureが絡むと厄介だね>トランスレータ
0450439NGNG
>>442 レスどうもありがとう。
ちなみに私は、Chem3Dに食わせるファイルを作成するのに(分子を
構成する原子の座標の計算)、Schemeを使っています。
0451デフォルトの名無しさんNGNG
(define (test)
 (let loop ((x 0))
  (lambda ()
   (display x) (newline)
   (loop (+ x 1)) )))
(define a (test))
(set! a (a))
0
(set! a (a))
1
(set! a (a))
2
こういうのだと、どういう風にCに変換されるのか、
ちょっと想像付かない。
全部gotoにするとかしないと、無理じゃないか?
0452デフォルトの名無しさんNGNG
ああ、これだったらちゃんと変換するや。かしこいね。
0453デフォルトの名無しさんNGNG
lispは名前付けるのに困らなくいいね。
とりあえずlambdaで作業始められる。
0454デフォルトの名無しさん NGNG
lispってここではじめて知って情報なんとかってシリーズの本を
見てみたんですけど、何がなにやら・・・・
リスト処理言語とか書いてありましたけど、どんなことに使うとよい
言語なんですか?
0455デフォルトの名無しさんNGNG
昔は、Lisp=人工知能
って感じだったけど、
今は、・・・、もっぱら研究用言語かな?
0456デフォルトの名無しさんNGNG
>>453
禿げしく同意
0457デフォルトの名無しさんNGNG
ではみなさんは何のために使っているんですか?
自分も単に触ってみたいと思っただけなのですが。
0458デフォルトの名無しさんNGNG

ボキュは、この本を読むためにSchemeの勉強しました。
絶対に読む価値あります。
http://www.mmjp.or.jp/pearsoned/washo/prog/wa_pro20-j.html
0459デフォルトの名無しさんNGNG
>>457
ある程度の定石さえ知っていれば、色んな処理がお手軽に書けるから、とか。
それと、自分にフィットする様に、言語自身に手直しを加える事が簡単なんだよ。
これはライブラリを作っていく様な事とは違う達成感がある。
0460457NGNG
>>458
ワタシも読んでみたくなりました。
0461デフォルトの名無しさんNGNG
基本的な事だけど、
シンボルが記号として、同一判定できるのがいい所だと思う。
文字列のままだと同値判定(strcmp相当)するしかないが、
文字列→シンボル変換すれば以後、
同一判定(ポインタ値の比較)だけで済む。
0462デフォルトの名無しさんNGNG
.emacs をカスタマイズするために使うだけなので、Emacs-Lisp の
ごく簡単な構文しかしらないな…。
0463デフォルトの名無しさんNGNG
>>462
lisp自体、複雑な構文はそれほど無いと思う。
構文唐を組み合わせれば複雑にもなるけど・・・。
0464デフォルトの名無しさんNGNG
演算子が無い、ということは必然的に優先順位とかも無い。
syntaxを除いて、括弧のネストのレベルで評価される順番が決まる。
そういう意味で覚える事は少ない。
lispはコードを応用できるかどうかが肝。
0465デフォルトの名無しさんNGNG
実際、quote lambda if define set!とか以外の構文は全部
マクロで作られた構文唐、ってscheme処理系は結構あるみたいね。
0466デフォルトの名無しさんNGNG
>>423
beginがlambdaで構成されてたらアウト。
(define-macro (begin . l) `(lambda () ,@(cdr l)))
こういうやつだった場合ね。
eval使うしか無いんじゃないかと思う。
0467デフォルトの名無しさんNGNG
こうだった。`((lambda () ,@(cdr l)))
0468デフォルトの名無しさんNGNG
(define (・∀・) 'イイ!)
(・∀・)
=>イイ!
0469デフォルトの名無しさんNGNG
>>466
そういう場合はletの結果をdefineすれば良いと思います。
 `(define ,pkg-name
  (let ()
   (load ,fn (current-environment))
   (make-package (car (current-environment)))))
0470デフォルトの名無しさんNGNG
>>469
なるほど・・
なかなかトリッキーなコードに見えるけど、
schemeではこういうのが普通の発想なのか
0471デフォルトの名無しさんNGNG
>>470
トリッキーに見えるのは恐らく、コードと環境を一緒に考えてるからだと思う。
0472デフォルトの名無しさんNGNG
Schemeのオブジェクトは、どこかで参照されてる限り消えないので、
ブロックから抜けてもそこで生成したローカル変数が使える?
0473デフォルトの名無しさんNGNG
>>472
objectは*永久に消えない*事が保障されてる。
ただしどこからも参照されなくなったobjectはgcで
勝手に回収されるのでメモリ不足とかの問題は起きない。
ローカル変数と言っても、中身はconsやstringとかで
動的に作られたobjectと一緒。
C++で言えばnewされたobject。
0474デフォルトの名無しさんNGNG
こんなんがあった。

「普通のやつらの上を行け 」
http://www.shiro.dreamhost.com/scheme/trans/beating-the-averages-j.html
0475デフォルトの名無しさんNGNG
letは値を局所的な名前でアクセス出来るようにフレームを作るだけで
値になるobjectまで生成するわけでは無いよ。(フレーム構成はobjectの集合だけど)
だから
(define (f i) (let ((a i)) (lambda()a)))
とした時、aはiに関連付けされた値をそのまま継承する。
fはclosureを生成して返すが、そのclosureはaを参照してる
ので、aの寿命はclosureと同じ期間に延長される。
(define x 0) ; 0 -> z
(define y (f x)) ;closure -> y
(eq? z (y)) ;object:0の同一性判定
=>#t
(eq? y (f x));object:closureの同一性判定
=>#f
0476475NGNG
まちがえた
s/x/z/g
0477475NGNG
で、>>469は(let()・・・)で作成した空のフレーム環境を使って
外部ファイルをloadして、そのフレームを返すclosureを作り、
そのclosureをpkg-nameにdefineする。
そのまま475のaがフレームに変わったと思えばいい。
0478475NGNG
ちなみに標準的なloadには環境を設定する引数は取れないけど、
evalを直接呼んでそう言う風に作り直せる。
(define (load fn env)
 (call-with-input-file fn (lambda (r)
  (let loop ((s (read r)))
   (if (eof-object? s))
    'end
    (begin (eval s env) (loop (read r)))) ))))
0479475NGNG
>>474
かなり前にがいしゅつっぽい
0480475NGNG
s/(eof-object? s))/(eof-object? s)/
0481デフォルトの名無しさんNGNG
>>479
スマソ
0482デフォルトの名無しさんNGNG
John McCarthy's Home Page
http://www-formal.stanford.edu/jmc/
0483デフォルトの名無しさんNGNG
クロージャの環境って、作った時点の環境で固定かと思ったけど、
(eval '(lambda()〜) env)
ってやれば適当な環境が見えるクロージャ作れるんだね。
0484デフォルトの名無しさんNGNG
evalを使えば当然できる事だとは思うけどね。>483
応用として、evalの結果を使ってまた別の環境にbindとかすれば、
全く関係の無い環境から、他の環境を操作できる。
(eval '(define name (eval '(lambda()〜) env2)) env1)
これでenv2で作成したclosureをenv1からnameで参照できる。
頭硬くなると、こういう発想がなかなかできなくなって苦労する・・。
0485デフォルトの名無しさんNGNG
いくつかのlispの処理系は、環境をalistとして取り出せるみたいだけど、
この辺まで規格化すると、実装に影響でるのかな?
0486デフォルトの名無しさんNGNG
クロージャってなんですか?
0487デフォルトの名無しさんNGNG
Steve Majewski によるクロージャーの特徴づけ

オブジェクトとは、処理が付加されたデータのことです。
クロージャーとは、データが付加された処理のことです。

dW : Linux : Pythonでの関数プログラミング (第2回)
http://www-6.ibm.com/jp/developerworks/linux/010706/j_l-prog2.html

原文
http://www.ibm.com/developerworks/linux/library/l-prog2.html
0488デフォルトの名無しさんNGNG
C++Builderにも__closureつうのがあるね。
同じ物かは知らないけど。
void (__closure *func)();
0489デフォルトの名無しさんNGNG
lispでのクロージャは、定義された場所から見える局所的な
環境が参照できる関数オブジェクト
環境がどこかで変更されれば、それを参照している
クロージャ自体も影響を受ける。
0490デフォルトの名無しさんNGNG
>>488
あれは、delphiでいうTMethod型、つまり
あるObjectポインタと、そのObject用のどれか1つのメソッドのポインタ
のペア、だな。
なるほど、>>487の説明にドンピシャ一致してるかも(わら
0491デフォルトの名無しさんNGNG
>>487を踏まえて整理すると、
普通の関数とクロージャの違いは状態(データ)を持つかどうかで、
オブジェクトとクロージャの違いは、
データ主体か関数主体かの違いって事ですかね・・?
0492デフォルトの名無しさんNGNG
関数主体じゃなくて、処理主体でした。
「主体」って表現自体が曖昧っぽいですが。
0493デフォルトの名無しさんNGNG
>>491
状態というか、そのクロージャを作った場所での環境が見える。
0494デフォルトの名無しさんNGNG
lispのはレキシカルクロージャというらしい。
どっかのサイトに書いてあった。
0495デフォルトの名無しさんNGNG
>>493
491はネストしたクロージャを想定していないから、状態と環境の違いが
わかりにくいんだろう。
0496デフォルトの名無しさんNGNG
「As far as Lisp is concerned, the words we have been using in the lists cannot be divided into any smaller parts and still mean the same thing as part of a program;
likewise with numbers and single character symbols like `+'. 」

これの日本語訳が

「Lisp について話している限りは、我々がリストの中で使ってきた単語は、それ以上小さなプログラムのパートには分解出来ない。それは数字や `+' みたいな一つの文字からなる記号でも同じである。」

となっていますが、なんか違うような気がします。

特に
「mean the same thing as part of a program」
の部分がよくわかりません。
0497俺的意訳NGNG
Lispについて話している限り、我々がリストの中で使ってきた概念
はほかのより小さな概念を使って説明できるものではない。
プログラムについても同じことが言える。たとえば+という一文字
の記号ですらそうである。
0498デフォルトの名無しさんNGNG
レキシカルスコープ/クロージャ
http://www.geocities.co.jp/SiliconValley-Oakland/1680/xyzzy_lisp/xyzzy25.html
0499名無λ式NGNG
>>496
わざと仰々しく書いている文章上の遊びを無視すると、
「Lisp におけるリスト用語は、これ以上分割することは不可能であり、
プログラム中においても同じ意味であり続ける。
数や `+' のようなたった一文字の記号と同じように。」

"still"は「不変」を強調している。

要するに、car, cdr, cons, nil, (, ), ドット対のドット, "cons cell"などは、
数と四則演算のように、基本的でかつ身近なもので、
carが「フィボナッチ数列を計算する関数」の名前になるなんて事はありえない、
それほどLispとLisperにとって"list"は身近なもんなんだ、ということ。
0500500!NGNG
Haskellスレが立ってますね。
関数型プログラミング言語Haskell
http://piza2.2ch.net/test/read.cgi?bbs=tech&key=996131288
0501デフォルトの名無しさんNGNG
schemeとかって関数の引数の評価順序って決まってるんですか?
(define (func a b) (cons a b))
(define x 1)

(func x (begin (set! x 2) x))
=>(1 . 2)
0502デフォルトの名無しさんNGNG
あとこんなのとか。
(let ((test 0))
 (define (local-func) (set! test (+ test 1)))
 (func test (local-func))
)
一時変数用意した方がいいですか?
0503無能な姦理人@Shiri-QNGNG
□□□□■□□□□□■□□□□□□□□□□□□□□□□□□□□□
□□□■■□□□□□■□□□□□□□■■■■■■■■■■■■□□
□□■■□□□□□■■■■■■□□□□□□□□□□□□□■■□□
□■■□□■□□□■□□□□■□□□□□□□□□□□□■■□□□
□□■□■■□□■■■□□■■□□□□□□□□□□□■■□□□□
□□□■■□□■■□■■■■□□□□□□□□□□□■■□□□□□
□□■■□□□□□□□■■□□□□□□□□□□□■■□□□□□□
□□■□□□■□□□■■■■□□□□□□□□□□■□□□□□□□
□■■■■■■□□■■□□■■□□□□□□□□□■□□□□□□□
□□□□■□□□■■□□□□■■□□□□□□□□■□□□□□□□
□□■□■□■□□□□■■□□□□□□□□□□□■□□□□□□□
□□■□■□■□□□□□■■□□□□□□□□□□■□□□□□□□
□■■□■□■□□□□□□□□□□□□□□□□□■□□□□□□□
□■□□■□□□□■■■□□□□□□□□□□□□■□□□□□□□
□□□□■□□□□□□■■■□□□□□□□□□□■□□□□□□□
□□□□■□□□□□□□□■■□□□□□□■■■■□□□□□□□





続きはコチラです
http://www.geocities.com/entry_k/main/main01.html
0504デフォルトの名無しさんNGNG
>>501
R5RSの「4.1.3 プロシージャ呼び出し」に、
「評価の順序は規定されていない」と書いてある。
0505デフォルトの名無しさんNGNG
>>504
こういうコードってうっかり書いてしまいそうになりませんか?
lispだと関数の引数に関数呼出しを続けて書くケースが多いのも
関連してると思いますが、結構気を付けていても、
知らず知らずの内に・・って場合が結構ありそう。
0506無名λ式NGNG
>>505
私は、引数の評価順序が決まっている言語でも、
引数の評価順序に依存しないprogram書く習慣です。
別人(後日の自分も含む)が見た時も理解しやすいよん。

Lispだからといって、返値使いまくるprogramも嫌いだな。
0507デフォルトの名無しさんNGNG
>>505
(func a (begin (set! a (+ a 1)) a))
の場合は、
(let* ((t1 a) (t2 (begin (set! a (+ a 1)) a)))
 (func t1 tt2))
という風に一時変数を挟めば評価順序を自分で制御できます。
0508507NGNG
でも、評価順序の制御のためだけに、わざわざ一時変数を手書きで
挟むのも馬鹿らしいので、左から右(あるいは右から左)へ
評価される様に、let*やletrecを使ったマクロを定義して形式化
するのがいいかもしれません。

;左から右への評価順序を強制するマクロ。
(define-macro (ltor-args func . args)
 (let ((tmp (map (lambda (x) (gensym)) args)))
  `(let* ,(map (lambda (x y) (list x y)) tmp args)
   (,func ,@tmp) )))
0509507NGNG
>>508のマクロの使い方
(ltor-args func a (begin (set! a (+ a 1)) a))
これは
(let* ((G10 a) (G11 (begin (set! a (+ a 1)) a)))
(func G10 G11))
という風に展開される。
0510507NGNG
;ついでに、右から左への評価順序を強制するマクロ。(reverseしてるだけ)
(define-macro (rtol-args func . args)
 (let ((tmp (map (lambda (x) (gensym)) args)))
  `(let* ,(map (lambda (x y) (list x y)) (reverse tmp) (reverse args))
   (,func ,@tmp) )))
0511507NGNG
>>506
その習慣が一番良いでしょうね。

例えばC言語にトランスレートされたりする状況を考えると、
>>501の様なコードを変換するとそのまま不具合まで継承される恐れがある。
(C言語も引数の評価順序は定められていないので)
これは賢いトランスレータを使ったとしても同じだと思います。
0512無名λ式NGNG
>>511
Schemeの設計された年代を考えると、
並列化scheme方言の事まで視野に入れたと考えたとか、
研究テーマとしてcompilerのoptimizeを追求したかったという事も考えられるけど、
SICPなんか見るとやっぱりWhat you see is What the program meansって、
考えがあると思います。暗黙の評価順序はそういう考えに反するのでしょう。

今時、引数の評価順序が決まっている言語、(゚Д゚)ハァ?とさえ思ってしまう。

ltor-argsはその点明示的でいいね。マクロとS式のメタプログラミング炸裂だし。
0513デフォルトの名無しさんNGNG
501です。
>>504 >>506 >>507
ありがとうございます。大変参考になりました。
なんか今までbeginのノリで書いてた様な気がします。(やべー
なんていうか、scheme(っていうかlispですか?)のマクロって凄いですね。
他の言語ではずっと悩みそうな問題が一発で解決したような気がします。
(ltor-argsありがたく使わせてもらいます。)
こういうのメタプログラミングっていうんですね。
0514507NGNG
>>510は
 (reverse (map (lambda (x y) (list x y)) tmp args))
にした方がスマートでした。(こっちはあんまり使わなさそうですが)

>>513
lispのマクロは既存の構文と同等に扱えるので作り甲斐があると思います。
0515デフォルトの名無しさんNGNG
.NET対応のlispって無いの?
0516デフォルトの名無しさんNGNG
うーむ、さっぱりわからん
0517デフォルトの名無しさんNGNG
>515 ちょっと探してみたけど、ないみたい。
0518デフォルトの名無しさんNGNG
Lisp で GUI なプログラミングはどうするんでしょう? STkですか?
Lisp でネットワークなプログラミングはどうするんでしょう? CL-HTTP あたりのソース読め?
0519無名λ式NGNG
>>518
http://siag.nu/
http://www.gnu.org/software/guile/guile.html
http://www.gimp.org/scripts.html
あたりも。
0520デフォルトの名無しさんNGNG
>>515
これは?
.NET対応Lispコンパイラ
http://www.atmarkit.co.jp/fdotnet/special/dotnet_sdk_part2/dotnetsdk05.html
現物触わった事ありませんが。
0521デフォルトの名無しさんNGNG
Side effect
の日本語訳が
副作用
になっていますが、「クスリの副作用」など、あまり良いイメージがありません。
そこで、
「2次効果」
と改訳したいと思いますが?
0522俺様訳NGNG
「If evaluation applies to a list that is inside another list, the outer list may use the value returned by the first evaluation as information when the outer list is evaluated. 」

女の子の服を脱がすときに、Lisp はまず、一番肌に近いブラジャーを脱がします。
つぎに、その外側につけてるシャツを脱がします。
最後に、一番外側に着ているカーディガンを脱がします。

これが Lisp のやり方です。
0523デフォルトの名無しさんNGNG
>>521
side effectに言及したがる人は、それを悪役にしたがる人で
ある場合はほとんどですから、あまり良いイメージのない「副
作用」で十分なのでせう。
0524デフォルトの名無しさんNGNG
え!! >522
0525デフォルトの名無しさんNGNG
>>522

やはり Lisp ってマニアックですね。
0526デフォルトの名無しさんNGNG
>>522
ちょっとまって、
(カーディガン (シャツ (ブラジャー 女の子)))
なの?
0527デフォルトの名無しさんNGNG
defmacroとdefine-macroってどう違うんですか?
0528デフォルトの名無しさんNGNG
>>527
defmacroはcommon-lisp流の書式で、
define-macroはscheme流の書式。
common-lisp: (defmacro name args body)
scheme: (define-macro (name args) body) または
    (define-macro name (lambda (args) body))
単に書式の違いなので、処理系によっては両方用意されてたり
自分で定義もできるけど。
defunとdefineの関係と似てる。
0529デフォルトの名無しさんNGNG
あとdefine-macroと同じ書式の
(defmacro (name args) body)
という書き方や
(macro name (lambda args body))
というのもある。(古い処理系に多い)
0530デフォルトの名無しさんNGNG
>>528解説どうもです。
なるほど・・・たとえばDrSchemeだとdefine-macroの書式が使えるみたいですね。
0531デフォルトの名無しさんNGNG
SCMはえー
0532デフォルトの名無しさんNGNG
>>530
DrSchemeって`(quasiquote)使えなくない?
同梱のMzSchemeは使えるのに。どういう仕様なんだょぅ〜
0533デフォルトの名無しさんNGNG
>>532 それは多分languageっていう設定が、
Beginning Studentになってるからだと思う。
Full Schemeとかにしてみては?
0534デフォルトの名無しさんNGNG
>>513
MIT-Schemeだと右から左に評価されるみたいです。
というわけで、完全に実装依存っぽいです。>評価順序
0535無名λ式NGNG
>>534
> というわけで、完全に実装依存っぽいです。>評価順序

仕様としては「未定義」です。実装ごとに違って不思議はないです。
それどころかversionごと、compile毎にかわって良い。> 「というわけで」
0536デフォルトの名無しさんNGNG
>>533
あ、やっぱり設定の問題ですか。
0537デフォルトの名無しさんNGNG
参考までにdefine-macroで定義したdefmacro
(define-macro (defmacro name args . body)
  `(define-macro ,(cons name args) ,@body) )
または
(define-macro defmacro (lambda (name args . body)
  `(define-macro ,name (lambda ,args ,@body) ))
機能的にはCommonLispのやつには及ばないだろうけど
0538デフォルトの名無しさんNGNG
上のdefmacroで定義したdefun
(defmacro defun (name args . body)
  `(define ,name (lambda ,args ,@body)) )
0539デフォルトの名無しさんNGNG
evalマンセー
0540デフォルトの名無しさんNGNG
apropos
って、今辞書で調べたら
アプロポウ
って発音するんですね。
いままで
アプロポス
って読んでました。
0541デフォルトの名無しさんNGNG
ハァ?
0542デフォルトの名無しさんNGNG
最近出たR5RS対応のSchemeの本、2冊本屋にあったんで初めて読んで見たけど、
define-macro/defmacroとかのlisp形式マクロの説明がまるっきり省かれてた。
(まるで初めから存在しなかったかの様で、ちょっと悲しかった。)
入門書としてはdefine-syntaxとかsyntax-caseは仕様的には綺麗かもしれないけど、
いきなり載せても直感的には判りにくいから、標準じゃないにしても、
まずお手軽で実装も簡単なlisp形式マクロについて説明して、それの問題指摘と
define-syntaxに至った経緯とかを解説して欲しかった気がする。
ここに書いてもしょうがないけど。
あと、evalや環境辺りの説明はやっぱり弱かった。
(規格書以上の事はやっぱり書かれていない。)
0543デフォルトの名無しさんNGNG
SLIBの解説でdefmacroの説明はあるよ(日本人が書いた方の本)
0544デフォルトの名無しさんNGNG
> 542 名前:デフォルトの名無しさん投稿日:2001/08/03(金) 02:04
…中略…
> define-macro/defmacroとかのlisp形式マクロの説明がまるっきり省かれてた。
> (まるで初めから存在しなかったかの様で、ちょっと悲しかった。)
> 入門書としてはdefine-syntaxとかsyntax-caseは仕様的には綺麗かもしれないけど、
> いきなり載せても直感的には判りにくいから、標準じゃないにしても、

「直感的には判りにくい」と思うのはdefmacroが脳味噌にしみついてるからじゃ
ないの。入門者から見たらhygienic syntaxのほうがずっと直感的だと思うぞ。

> まずお手軽で実装も簡単なlisp形式マクロについて説明して、それの問題指摘と
> define-syntaxに至った経緯とかを解説して欲しかった気がする。

こっちはまぁおっしゃるとおり。
0545デフォルトの名無しさんNGNG
>>544
>defmacroが脳味噌にしみついてる
実はそうです(w
結局自分にしてもsyntax-rule/syntax-caseを日本語で解説してる本
という事で非常に価値がありました。
(あの辺、R5RS規格書だけ見てもさっぱりわからないと思う)
0546デフォルトの名無しさんNGNG
久々にネタ提供
いちいちrequire指定して外部ファイルを読みこませるのが
馬鹿らしくなったのでこういうの作ってみました。
外部ファイルを遅延ロードさせる関数です。
(関数が呼び出された時点でロードする。)

(define (ondemand fn sym-list)
  (define (regist s)
    (eval `(define-macro (,s . x)
             (if (require ',fn)
                 (cons ,s x)
                 (error "ondemand load failure" ',fn) ))
          (interaction-environment) ))
  (if (symbol? sym-list)
      (regist sym-list)
      (for-each regist sym-list) ))
0547デフォルトの名無しさんNGNG
補足
・requireがマクロ→関数の上書きをしてくれないと機能しない。
・requireはloadでも代用できます。
・requireは 成功時#t 失敗時#f を返す実装であること。
これはロード中にエラーが発生した場合の対処。無くてもいい。
(requireでロードされるファイルに同名の関数が存在しないと無限ループになる。)

使い方
初期化ファイルなどに↓を置いておく
(ondemand 'trnscrpt '(transcript-on transcript-off))

こうすると、初期化ファイルが読まれた時点で仮のtranscript-on transcript-off
が定義される。
(transcript-on "log")
などとして関数を呼び出すと、そのときにtrnscrpt.scmを読みに行き、
transcript-on transcript-offが本来の関数にすげ変わり、その関数を再評価する。
0548デフォルトの名無しさんNGNG
これでインタプリタの起動が数割程速くなりました。

問題点は、処理系依存な部分がありそうなんでどの環境でもそのまま動くとは限らない。
特に、ondemandで登録した関数は最初マクロとして定義されるので、
applyで呼び出されるとまずいかもしれない。(うちの環境では大丈夫だけど)
0549デフォルトの名無しさんNGNG
あとclosureじゃないから、関数引数経由で評価される場合も
まずいかもしれない。
((lambda (p) (p "log") ) transcript-on)
とした場合。
0550デフォルトの名無しさんNGNG
良く考えたら、普通の関数に対してはマクロ展開する必要は無いから、
仮関数を普通の関数にして、その中でapplyすれば解決する。
(define (ondemand-func fn sym-list)
  (define (regist s)
    (eval `(define (,s . x)
             (if (require ',fn)
                 (apply ,s x)
                 (error "ondemand load failure" ',fn) ))
          (interaction-environment) ))
  (if (symbol? sym-list)
      (regist sym-list)
      (for-each regist sym-list) ))

このondemand-funcを併用すれば、>>548-549で言われた問題が解決する。
(マクロの遅延ロードに対しては>>546を使う。)
0551デフォルトの名無しさんNGNG
自己書き換えだね>550
0552デフォルトの名無しさんNGNG
そう思う>551
0553デフォルトの名無しさんNGNG
>>551
evalって自己書き換え保証してるの?
0554デフォルトの名無しさんNGNG
>>553
MzSchemeとDrSchemeでは動きました。(loadに変更した)
仕様書には明確に書かれてないみたいですが、自己書き換えで
現在の継続が失われる様な処理系は多分ないと思います。
0555デフォルトの名無しさんNGNG
それに自己書き換えと言ってもこの場合、
require(またはload)で新しくclosureを作成し、
それをbindし直すので。
仮関数のclosureの継続には影響されない筈。
(少なくともrequireからの戻り、apply以降の継続は存在してる)
0556デフォルトの名無しさんNGNG
本当の意味での書き換えは、既存のオリジナルコードを
何らかの手段で取り出して直接加工した場合。
それで自己書き換えする場合は、よほど注意深くやらないと
おかしな事になります。(相互書き換えならまだ容易ですが)
0557デフォルトの名無しさんNGNG
defmacroで作ったsyntax-caseとかって無いですか?
(CommonLispからでも使える様なやつ。)
なんか大袈裟なコードのしか見かけないんで。
0558デフォルトの名無しさんNGNG
dfmacroによるdefine-syntax(syntax-rule)の実装で、
mbeというのがある様です。>557
0559デフォルトの名無しさんNGNG
これです。
Scheme Macros for Common Lisp
http://www.cs.rice.edu/~dorai/mbe/mbe-lsp.html
でも説明を見る限り、hygienicの対応が不完全な様です。
0560デフォルトの名無しさんNGNG
>>559
ありがとう
0561デフォルトの名無しさんNGNG
SCMのSLIBはdefmacro、STkはdefine-macroで作られてるからそれ移植するか、
pseudo-schemeとか使って適当にscheme->commonlispすればいいんじゃないかと思う。
0562デフォルトの名無しさんNGNG
Lisp/Scheme でソケットなネットワークプログラミングな解説を
しているサイト、書籍ってありませんか?

あとはどの処理系ならできるとか。
0563名無しNGNG
Scheme について質問。
というかだれかお助けを。

問題で以下のようなものをだされました。

リストを集合としたとき、その部分集合全体の集合を表すリストを
かえす手続きを作成せよ。

どなたかおねがいです。
0564562NGNG
MIT Scheme の Reference に 15.8 TCP Sockets というのが
ありましたね。

本当は UDP がしたいんだけどな。
0565563NGNG
全く同じなのですが組み合わせの問題です。
すべての組み合わせを返すものをつくれということです。
たのんます。
0566無名λ式NGNG
>>563
再帰で考えろ。以上。
0567デフォルトの名無しさんNGNG
>>565
ちょっと前に作ったやつ
(define (ex efrom eto er)
  (let G45 ((G41 efrom) (G42 eto) (G43 er) (G44 '()))
    (let G47 ((G46 G41))
      (cond
        ((<= G46 G42)
          (cond
            ((< 0 G43)
              (if (not (memv G46 G44))
                (let ((G48 (G45 G41 G42 (- G43 1) (cons G46 G44))))
                  (if (and (pair? G48) (pair? (car G48)))
                    (append G48 (G47 (+ G46 1)))
                    (cons G48 (G47 (+ G46 1)))))
                (G47 (+ G46 1))))
            (else (reverse G44))))
        (else '())))))

0〜3(4桁)までの組み合わせ全部
>(ex 0 3 4)
=>((0 1 2 3) (0 1 3 2) (0 2 1 3) (0 2 3 1) (0 3 1 2) (0 3 2 1) (1 0 2 3) (1 0 3 2)
(1 2 0 3) (1 2 3 0) (1 3 0 2) (1 3 2 0) (2 0 1 3) (2 0 3 1) (2 1 0 3) (2 1 3 0)
(2 3 0 1) (2 3 1 0) (3 0 1 2) (3 0 2 1) (3 1 0 2) (3 1 2 0) (3 2 0 1) (3 2 1 0))
0568デフォルトの名無しさんNGNG
autoload>546
0569デフォルトの名無しさんNGNG
>>568
schemeには無いよ
つーかCommonLispにも無いけど
emacs?
0570無名λ式NGNG
librepにもautoloadありまっせー。sawfishとかで使っているぅ。
0571デフォルトの名無しさんNGNG
面白そうなんでlibrep落としてきた。
sawfishも面白そうだけど自分は普段windows環境なので
使えないのだった。cygwinでなんとかならないかな
とりあえずlibrepだけでも動けばいいけど
0572デフォルトの名無しさんNGNG
>>546-550
なにげにスゲー便利だった。>関数呼出し一発ロード
057318NGNG
日本語のページが見つかったから一応貼っておく
Sawfish JP
http://sawfish.gnome.gr.jp/index-ja.html
0574デフォルトの名無しさんNGNG
(lambda (x) (f x)) - > f
((lambda () x)) - > x
((lambda (x) (f x)) y) - > (f y)
みたいに、式を単純化するプログラムってありませんか?
0575デフォルトの名無しさんNGNG
それぐらい自分でなんとか作れない?>574
0576デフォルトの名無しさんNGNG
>>567
それは順列ではないか?

>>563, >>565
SICPのExercise 2.32より(一部変更)

(define (subsets s)
(if (null? s) (list '())
(let ((rest (subsets (cdr s))))
(append rest (map (lambda (x) (cons (car s) x)) rest)))))

Exerciseでは、(lambda (x) (cons (car s) x)) が <??>になっている。
実行例
(subsets '(a b c))
(() (c) (b) (b c) (a) (a c) (a b) (a b c))
0577しおりNGNG
(push-mark) ;ここまで読んだよ
0578デフォルトの名無しさんNGNG
>>574
そういうのはコンパイラとかのソースに含まれてる
と思うんで、そういうコード探してみては?

汚いけど一番最初のやつだけ
(lambda->nop '(lambda (x y z ...) (f x y z ...))) => f
(lambda->nop '(lambda () (f))) => f

(define (lambda->nop x)
  (and (pair? x)
       (eq? (car x) 'lambda)
       (pair? (cdr x))
       (pair? (cddr x))
       (null? (cdddr x))
       (pair? (caddr x))
       (symbol? (caaddr x))         ; (f ...)の形式
       (equal? (cadr x) (cdaddr x)) ; 引数の比較
       (caaddr x) )) ;fを返す
0579デフォルトの名無しさんNGNG
パターンマッチさせた方が良いと思われ
0580デフォルトの名無しさんNGNG
JACAL
http://www.swiss.ai.mit.edu/~jaffer/JACAL.html
0581デフォルトの名無しさんNGNG
http://www.gnu.org/manual/emacs-lisp-intro/html_mono/emacs-lisp-intro.html

↑このマニュアルを自分なりに改変して再配布しようと思ってますが、GPLなので問題無いですよね?
0582デフォルトの名無しさんNGNG
オリジナルの入手先をちゃんと貼っておけば問題無いと思います。>581
0583デフォルトの名無しさんNGNG
The Sugar Homepage
http://sugar.mini.dhs.org/
0584デフォルトの名無しさんNGNG
soft-scheme
http://www.intertrust.com/star/wright/code.html
0585デフォルトの名無しさんNGNG
昨々日The Little Schemerを購入したんだけど、
なにげにスゲー面白いね。
なぜ翻訳が出ないのかしら。
Scheme入門というだけでなく、再帰処理入門としてもステキな出来だと思うけど。
0586名無しさんNGNG
「Scheme手習い」(啓学出版)で訳が出てた奴?
つーかLisperでなくてもLispの本は参考になるから
いいぞーって言いたいトコ。
0587デフォルトの名無しさんNGNG
しつもんです。
(define test (let ((i 0)) (lambda () (set! i (+ i 1)) i)))
testは初期値0で、評価するたんびに+1された値を吐き出します。
(test) => 初回は1
(test) => 2
(test) => 3
んで、
ある関数に引数を多く渡した場合、半端な引数は
評価される事が保証されてるんでしょうか?
(話を簡単にするために、引数の評価順序は左から右という事にしておいてください)
((lambda (x y) (+ x y)) (test) (test) (test) (test))
これを評価した場合、
以降の
(test)
で3が返るのか、5が返るのか、引数が多いとエラーになるのか、
それとも決まってないのかが知りたいです。
ちなみに自分の所では3が返りました。
0588デフォルトの名無しさんNGNG
間違えました。
こうすると、
(define test (let ((i 0)) (lambda () (set! i (+ i 1)) i)))
((lambda (x y) (+ x y)) (test) (test) (test) (test))
=>3
(test) =>5
自分の所では5が返ります。
0589デフォルトの名無しさんNGNG
つまり、半端な引数もちゃんと評価されるのかどうかが知りたいんです。
0590デフォルトの名無しさんNGNG
エラーなんじゃ??
0591デフォルトの名無しさんNGNG
and式中の各々の評価結果を次の式に使いたい場合、
いちいちletで一時的なバインド作成するのが面倒なので
こういうの作ってみました。なかなか便利だったので公開します。

(define-macro (letand meta . expr)
  (let loop ((x expr))
    (if (pair? x)
        (if (pair? (cdr x))
            `(let ((,meta ,(car x)))
               (and ,meta ,(loop (cdr x))))
             (car x) )
        #t )))
0592デフォルトの名無しさんNGNG
書式 (letand <一時変数として使うメタシンボル> [シーケンス])

メタシンボルを参照すると、直前の式の評価結果を返します。
(letand tmp 1 (+ tmp 2) 3 (+ tmp 4))
=>7
このマクロを展開するとこうなります。
(let ((tmp 1)) (and tmp (let ((tmp (+ tmp 2))) (and tmp (let ((tmp 3)) (and tmp (+ tmp 4)))))))
(この場合は全部定数の論理式なので、最適化したらただの7になりますが)
0593デフォルトの名無しさんNGNG
ちなみに
(letand tmp)
=>#t
これはandと同じ仕様。
letorは意味が無いのでありません。(直前の式の評価結果が全部#f)
同様のアイデアを検索したらLAND*というのが既にあるみたいですが、
letバインド風の余計な括弧が必要なので、
letandの方がスマートだと思います。
0594デフォルトの名無しさんNGNG
XML and Scheme
http://www.lh.com/~oleg/ftp/Scheme/xml.html

XMLをS式で表現するSXML
(XMLドキュメントの抽象構文木Abstract Syntax Tree)
他にXPath->SXPath XSLT->SXSLTなど
0595デフォルトの名無しさんNGNG
Schemeでモナド
http://www.lh.com/~oleg/ftp/Scheme/misc.html#monadic-io
0596デフォルトの名無しさんNGNG
>>593
>同様のアイデアを検索したらLAND*というのが既にあるみたいですが、

SRFI-2ね。
http://srfi.schemers.org/srfi-2/
0597デフォルトの名無しさんNGNG
(define-macro (letif meta test true false)
`(let ((,meta ,test)) (if ,meta ,true ,false)))
0598デフォルトの名無しさんNGNG
LISPでかかれたおもろいプログラムってある?
0599デフォルトの名無しさんNGNG
面白いかどうか知らないけど、
html2lisp
http://www.fides.dti.ne.jp/~liki/lisp/lisp2html.html
(みた感じ、なんか実装が適当っぽいですが。)
とか。

(html ()
(body ((bgcolor "red") (link #aabbcc))
ああああ
)
)
↓(ちゃんと表示されるかな)
<HTML>
<BODY BGCOLOR="RED" LINK=#AABBCC>
あああ
</BODY>
</HTML>
ドキュメントをS式で書いとけば、後で実行できたりして面白いかも。
0600デフォルトの名無しさんNGNG
しまったインデントが
(html ()
  (body ((bgcolor "red") (link #aabbcc))
       ああああ
  )
)

↓
<HTML>
  <BODY BGCOLOR="RED" LINK=#AABBCC>
  あああ
  </BODY>
</HTML>
0601デフォルトの名無しさんNGNG
http://xarch.tu-graz.ac.at/autocad/lisp/FAQ-link/msg00505.html
0602デフォルトの名無しさんNGNG
簡単なパターンマッチの例です。
(match メタシンボルのリスト パターン テストする式)
全てのメタシンボルが一致したら、メタシンボルをマッチした物に
置き換えたリストを返す。
1つでも一致しなかったら#fを返す。

(define (match meta-list ptn tst)
  (define (list-tail x k)
    (if (zero? k) x (list-tail (cdr x) (- k 1))))
  (define (memq-pos obj l)
    (let loop ((x l) (c 0))
      (and (pair? x)
           (if (eq? obj (car x))
               c
               (loop (cdr x) (+ 1 c)) ))))
  (let ((r (map (lambda (x) x) meta-list)))
    (define (match? x y)
      (cond
        ((pair? x)
          (and (pair? y)
            (match? (car x) (car y))
            (match? (cdr x) (cdr y)) ))
        ((string? x)
          (and (string? y) (string=? x y)))
        ((and (symbol? x) (memq x meta-list))
          (set-car! (list-tail r (memq-pos x meta-list)) y)
          #t )
        (else (eqv? x y)) ))
    (and (match? ptn tst) r) ))
0603デフォルトの名無しさんNGNG
テスト
(match '(何か) '((lambda () 何か)) '((lambda () (f x))))
=>((f x))

(match '(何か) '((lambda () 何か)) '((lambda () (f x) (g y))))
=>#f

(match '(何か) '((lambda () . 何か)) '((lambda () (f x) (g y))))
=>(((f x) (g y)))

(match '(λ引数 関数 関数引数) '((lambda λ引数 (関数 . 関数引数)))
'((lambda (a b c) (f x y z))))
=>((a b c) f (x y z))
0604デフォルトの名無しさんNGNG
; --- A Pure Lisp Interpreter in Lisp ---
(defun plisp ()
(defun pl-evalquote (func args env) (pl-apply func args nil))
(defun pl-apply (func args env)
(cond ((atom func) (cond ((eq func 'car) (car (car args))) ((eq func 'cdr) (cdr (car args)))
((eq func 'cons) (cons (car args) (car (cdr args)))) ((eq func 'atom) (atom (car args)))
((eq func 'eq) (eq (car args) (car (cdr args)))) ((eq func 'return) (car args))
((eq func 'exit) (bye))
(t (pl-apply (pl-eval func args) args env)))) ((eq (car func) 'lambda)
(pl-eval (car (cdr (cdr func))) (pl-pairlis (car (cdr func)) args env)))
((eq (car func) 'label) (pl-apply (car (cdr (cdr func))) args (cons (cons (car (cdr func)) (car (cdr (cdr func)))) env)))))
(defun pl-eval (e env) (cond ((atom e) (cond ((eq e nil) nil)
((eq e t) t) (t (cdr (pl-assoc e env)))))
((atom (car e)) (cond ((eq (car e) 'quote) (car (cdr e)))
((eq (car e) 'cond) (pl-evcon (cdr e) env)) ((eq (car e) nil) (princ "Undefined Func.")
(terpri) (bye)) (t (pl-apply (car e) (pl-evlis (cdr e) env) env)))) (t (pl-apply (car e) (pl-evlis (cdr e) env) env))))
(defun pl-evcon (e env) (cond ((pl-eval (car (car e)) env) (pl-eval (car (cdr (car e))) env))(t (pl-evcon (cdr e) env))))
(defun pl-evlis (args env) (cond ((eq args nil) nil) (t (cons (pl-eval (car args) env) (pl-evlis (cdr args) env)))))
(defun pl-pairlis (x y env) (cond ((eq x nil) env) (t (cons (cons (car x) (car y)) (pl-pairlis (cdr x) (cdr y) env)))))
(defun pl-assoc (x env) (cond ((equal env nil) (princ "Undefined Func.") (terpri) (bye))
((equal (car (car env)) x) (car env)) (t (pl-assoc x (cdr env)))))
(princ "--- A Pure Lisp Interpreter in Lisp ---) (terpri) (prog (env) (setq env nil)
(loop (terpri) (princ "=>") (princ (pl-eval (read) env)))))
0605デフォルトの名無しさんNGNG
LISPでLISPインタープリタを記述すると上の様になる…
(動作はGCLで確認済み)
0606デフォルトの名無しさんNGNG
数学板で
http://cheese.2ch.net/test/read.cgi?bbs=math&key=997418959&st=1&to=1&nofirst=true
「2の50乗を計算するには?」

という質問が出ていたので、Meadow で

(expt 2 50)
C-x C-e
とやったら、値がでかすぎたのか、
0
と表示されてしまいました。

どうしたらいいのでしょうか?
0607デフォルトの名無しさんNGNG
xyzzy でやったら出来た。xyzzy 最高!

(expt 2 50)
1125899906842624
0608デフォルトの名無しさんNGNG
LISP でBignumを使って見るとか!
0609デフォルトの名無しさんNGNG
http://www.gnu.org/manual/elisp-manual-20-2.5/html_node/elisp_21.html
いま、↑ここを調べたら、Lisp のInteger 型の取れる最大値は
134217727
らしいです。
なんでMeadowでできなくてxyzzyでできるんだろう?
0610デフォルトの名無しさんNGNG
ttp://www1.mirai.ne.jp/~gyo/xyzzy/xyzzy-list.html

xyzzyの標準機能

オーバーフローしらずの電卓
多倍長整数が使える・・・・お小遣いが国家予算を超える人向き
0611デフォルトの名無しさんNGNG
なんでもなにも、xyzzyはCommonLispだから>609
lisp汎用のbignumパッケージとか何処かに落ちてると思うから、
それ使ってみたら?
0612デフォルトの名無しさんNGNG
>>602のメタシンボルをletバインドで参照できる様にした物。

(define (tagged-list? l tag)
  (and (pair? l) (eq? (car l) tag)))
(define (strip-quote expr)
  (if (tagged-list? expr 'quote) (cadr expr) expr ))

(define-macro (match-let meta ptn tst . body)
 (let ((r (gensym)) (m (strip-quote meta)))
  `(let ((,r (match ',m ,ptn ,tst)))
   (and ,r (let ,(map (lambda (x)
              (list x (list 'list-ref r (memq-pos x m) ))) m )
          ,@body )))))

(match-let '(expr) '((lambda () expr)) '((lambda () (f x))) expr)
=>(f x)

(match-let (rest) '((lambda () . rest)) '((lambda () (f x) (g y) (h z)))
 (case (length rest)
  ((0) '())
  ((1) (car rest))
  (else (cons 'begin rest)) ))
=>(begin (f x) (g x) (h z))
0613デフォルトの名無しさんNGNG
×=>(begin (f x) (g x) (h z))
○=>(begin (f x) (g y) (h z))

(match-let (lp fp f) '(lambda lp (f . fp)) '(lambda (x y z) (func x y z))
 (if (equal? lp fp) f #f))
=>func

(match-let (lp fp f) '(lambda lp (f . fp)) '(lambda () (func))
 (if (equal? lp fp) f #f))
=>func
0614デフォルトの名無しさんNGNG
604>
LISPでLISPインタープリタを組むのはウインストンの本にも載ってるや〜ね
0615デフォルトの名無しさんNGNG
>>605
インデントしろよーとか言おうと思ったけど
長くなりそうだからやめた
LispOnLispはそのままだと遅いけど、
なんか速くする方法無いかな
0616デフォルトの名無しさんNGNG
Lispで仕事したいのですが、どこ行けばいいですか?
0617デフォルトの名無しさんNGNG
>>616
大学教授になりましょう
0618デフォルトの名無しさんNGNG
製品にLISP使ってそうな会社に無理やり就職する。>616
0619デフォルトの名無しさんNGNG
>>616 AutoCAD ってソフトに Lisp 付いてたよ
0620デフォルトの名無しさんNGNG
Emacs Lisp のみを受注生産するフリ−ぷろぐらまぁになる

例)リージョン内の改行コードを削除するマクロ → 3万円
0621デフォルトの名無しさんNGNG
図研のCAEソフトはマクロランゲージとしてschemeが組み込まれてる。
0622デフォルトの名無しさんNGNG
>>615
Lisp in Lispを高速化するには、コンパイルするだけじゃ、ダメかな?
コモンだったら、最適化しない?
0623デフォルトの名無しさんNGNG
日本Lispユーザ会
JLUG (Japan Lisp User Group)
http://jp.franz.com/jlug/index.html
0624デフォルトの名無しさんNGNG
素のLISPとLispOnLispの間に生じた差分を取って
その差をマクロ化するとか。
こういうの自動化できればいいんだけど。
0625デフォルトの名無しさんNGNG
だんだん Lisp の お勉強が おもしろく なって きて しまいました。
どう したら いいでしょうか?
0626デフォルトの名無しさんNGNG
そのまま、立派なLisperになって大成してください。
0627デフォルトの名無しさんNGNG
Lisp in Lisp で検索部分を線形探索じゃなくて、ハッシュにするというのはどう?
0628デフォルトの名無しさんNGNG
LISPでハッシュするには、配列や拡張データ型が必要だけどね。
0629デフォルトの名無しさんNGNG
>623

ttp://jp.franz.com/jlug/ja/resources/communities.html#community
↑
しっかり、2chのLISPスレッドもリンクされているところが凄い。
にしても、ACLは高すぎ。欲しい〜。
0630デフォルトの名無しさんNGNG
LISPでCGI&データベース連携
ttp://www.etl.go.jp/~matsui/eus/weld/weld.html
0631デフォルトの名無しさんNGNG
>628
スレッド全部読んでないので違う話だったらすいません。
CommonLispなんかだとハッシュというオブジェクトがはじめからあります。
(make-hash-table) ってやれば生成できて、
gethash っていうアクセサ使えば簡単に使えます。
ちなみにハッシュ・キーの等価チェック用の述語もeq eql equal
(第2版からequalpも)から選べます。
0632デフォルトの名無しさんNGNG
>>631
628です。不勉強で、すいません(藁)
いまだに、マッカーシーの原著論文+LISP1.5 Programmer's Manualだけで処理系を
実装してるもので(藁)
0633デフォルトの名無しさんNGNG
ちなみに、私のいる、大学院では、いまだにLISP1.5 Programmer's Manualを
使って、LISPの処理系の実装を講義されている先生がいらっしゃりますです。
0634デフォルトの名無しさんNGNG
www.civilized.comではLISP1.5をベースにしたLISP処理系をC言語で実装するテキスト
(勿論、ソースも附属)を配布してますぜ。
0635デフォルトの名無しさんNGNG
JavaScript to Scheme translator
http://sourceforge.net/projects/js2scheme/
0636デフォルトの名無しさんNGNG
>>633
もう図書館のこの本バラバラになりそうなんだよな。
コピーして持ってた方がいいかも。
0637デフォルトの名無しさんNGNG
>>606
(expt 2.0 50)
1125899906842624.0
0638デフォルトの名無しさんNGNG
>>612 のmatch-letを使った条件式の変形
(define (condition-optimize x)
  (or (match-let '(test e) '(if test e #f) x
        (list 'and test e) )
      (match-let '(test e) '(if test #t e) x
        (list 'or test e) )
      (match-let '(test t f) '(if (not test) t f) x
        (condition-optimize (list 'if test f t)) )
      ; ...
      x ))

(condition-optimize '(if (not a) b c))
=>(if a c b)
(condition-optimize '(if a b #f))
=>(and a b)
>(condition-optimize '(if a #t b))
=>(or a b)
(condition-optimize '(if (not a) #f b))
=>(and a b)
0639デフォルトの名無しさんNGNG
>>637
2.0 にしたらオーバーフロー起こさずに答えが出ましたよ!!
Meadow でも!!!
理由はわからんがすごい!!!!
0640デフォルトの名無しさんNGNG
>>639 emacs19 あたりから浮動小数点がついたからでは。
0641デフォルトの名無しさんNGNG
>>636
まだ、MIT PressからLISP 1.5 Programmer's Manualは販売されてるから、
絶版になる前に買っとくのが正解かもよ。
0642デフォルトの名無しさんNGNG
LISPで天下が取れますか?
0643デフォルトの名無しさんNGNG
LISP1.5ってだいぶ前の仕様だと思うけど
いまさらでも読む価値ありますか?>641
0644無名λ式NGNG
>>643
1.5の仕様はともかく、本の内容が面白いです。
"History of Lisp"なんかも面白い。
http://www-formal.stanford.edu/jmc/history/lisp/lisp.html
0645デフォルトの名無しさんNGNG
644に禿げしく同意!
0646デフォルトの名無しさんNGNG
>>643
LISP1.5は全てのLISPの基本となる、LISPの本質そのものともいえるもの。
そんな質問は愚問だと思う。
0647デフォルトの名無しさんNGNG
1ヶ月前、OOP・デザパタ萌え〜な私
↓
何気なく、SICPをチラッと見てみた
↓
面白そう、「チョット」やってみるか
↓
めっちゃ、面白いじゃん!lisp/scheme萌え〜
↓
(゚д゚)ウマ-
0648デフォルトの名無しさんNGNG
Lisp/Scheme系のプログラミングパラダイムに、「ストリーム(streams)」
というものがあって、

0.UNIXのファイル抽象とは無関係。:-P
1.状態の変化を変数への代入無しに表現する。
2.状態の時系列の変化を連続したデータのつながりとして表現する
3.遅延評価と高階関数によって実装する

というものらしいんですが、状態の変化を扱わざるを得ないGUIプログ
ラミングなどに応用できるものかどうか識者の見解をうかがいたいです。

読んだ本(SICP2nd)の例では bank-account の例が載ってましたが、口
座利用者の引出し額もストリームとして扱うことにしていて、そんなも
んどうやったら計算で得られるんじゃと頭を抱えてしまいました。
(洩れってアホですか?)
0649無名λ式NGNG
Atomic transactionのintention list方式って、
「額」じゃなくて「操作」のlistだけど、bank-accountのstream方式みたいなもんじゃん。
;; commitが起きる度に短くなっていくけど。
0650デフォルトの名無しさんNGNG
>>649
操作の待ち行列があればストリームと同じように扱えるからオッケーということですね
0651無名λ式NGNG
そうだす。
>>648の2,3は「『状態の変化』自体を『時系列を意識して』扱いたい」ということなのだから。

>>648のGUI云々って事で言えば、GIMPのundoの実装を見るよし。
control panelなんかも複数回のapplyの任意の段階に戻りたい時は履歴持つ必要あるよね?

Command patternも眺めてみてね。
0652デフォルトの名無しさんNGNG
Haskellの話しなんでsageるけど、
Fudgetって GUI frameworkは streamをつなぎまくって
GUI作ってたぞ。
0653無名λ式NGNG
>>652
pure functionalで状態扱いたい時は、そう(モナド系)するしかないっすね。
0654デフォルトの名無しさんNGNG
SCHEMEとCommon ユーザはどっちが多いかな
0655デフォルトの名無しさんNGNG
>>651
あれ、でも操作の待ち行列って変数に値としてため込まないといけないような…。
いや、遅延評価でなんとかなる…?

ああ、分からなくなってきた。
0656無名λ式NGNG
>>655
遅延評価云々は、未来の出し入れを無限リストで表現するからでしょ?
リストにpost-pendするんじゃなくて。

後はそんな難しい事は言ってないよん。
0657デフォルトの名無しさんNGNG
すいません、いままで
lambda
を
ランバダ
って読んでました。なぜそこで踊るのかといつもふしぎに思ってました。
0658デフォルトの名無しさんNGNG
>>657
よかったー自分だけじゃなかったんだあああ(w
0659デフォルトの名無しさんNGNG
http://homepage2.nifty.com/galaxystar/yool.htm
誰かこれ↑使ってる人いる?

「YOOL for Windowsの紹介<概要>YOOL for WindowsはWindows95以降で動作するLISPインタプリタです。オブジェクト指向プログラミングやWindowsアプリケーション作成も可能です。
<特徴>
 ・LISP1.9とCommon LISPの中間のような仕様。・スタックが深いので10000回程度の再帰呼び出しも可能。
・小さなプログラムを実行するときは少ないメモリしか消費せず、大きなプログラムを  実行すると自動的に大量のメモリを確保する。
・オブジェクト指向プログラミングをサポート。仕様は独自です。 ・WindowsのGUIを使ったプログラムの作成可能。 ・最大10個までのウインドを制御可能。
・32bitアプリケーションなので比較的高速。・サンプルプログラムとして、次のようなものを添付しています。
デジタル回路シミュレータ  英文和訳プログラム  お絵描きプログラム  スタック型のインタプリタ  各種ベンチマークテスト」
0660デフォルトの名無しさんNGNG
>>659
昔使ってたけど、ナンカなあ〜
0661デフォルトの名無しさんNGNG
>>659
付録のプログラムは結構有益だったけど。
0662デフォルトの名無しさんNGNG
>>659
>・スタックが深いので10000回程度の再帰呼び出しも可能。
「スタックが深い」ってどういう事だろう?
一回の関数呼出しに使うスタックサイズが小さいって事かな。
(スタックに使うメモリをヒープに置いてるとかなら、
そもそも制限は無い筈。)
使ったこと無いのでなんとも言えないです。
vectorにそれしか置いてないってのが不思議。
何か問題あるのかな>vector
0663無名λ式NGNG
>>662
Interpreterをもっている処理系では(compilerがあっても)、
stackを自前でheap上に管理するのよん。
0664デフォルトの名無しさんNGNG
LISPやってみたいのですが、開発環境が見つかりません。
フリーで手に入れられる開発環境はありませんか?

ちなみに一つだけ見つけてDLしたのですが、
使い方が良く分からなかったのです…
http://plaza10.mbn.or.jp/~lisp/
0665デフォルトの名無しさんNGNG
>>664
とりあえず >>624 を見ようね。
0666665NGNG
>>623 だった。鬱…。
0667デフォルトの名無しさんNGNG
ひとつだけ質問。
Lisp開発環境なるものを2つ入手したけど、どちらも、
CUIコマンドのように一行ずつ入力していくタイプだった。
Lispって、そういう入力形式なものなの?
それとも、たまたまそうだっただけの話?
1行ずつの入力で不便はないの?
0668デフォルトの名無しさんNGNG
>>667
不便。
でもファイルに書いて読み込むことも出来るはず。
0669デフォルトの名無しさんNGNG
>>667 >>668
(load "nantoka.l")
とかって無かったっけ?

それか Emacs を使うとか
0670デフォルトの名無しさんNGNG
user functionのない古いawkで書かれたLispをみたときは感動を通り越してあきれたYO
0671667NGNG
ん、では、LISPの開発環境って、伝統的に1行ずつ入力していく
ということでよろしいわけですね。
0672デフォルトの名無しさんNGNG
>>668 >>669 は読んでないの?
0673デフォルトの名無しさんNGNG
Schemeのcond構文で => てのがあるけど、これを言語仕様に含めることに必然性は
あるのだろうか。特に便利というわけでもなく、かつ激しく美しくない気がするのだが。
0674デフォルトの名無しさんNGNG
>>673
Schemeのcond-syntaxはlispでは昔からあったやつだから、
今更仕様を変えてしまうとlisperが混乱するってんで、
そのまま残してあるのでは?
=>はテスト結果を引数に、関数を呼び出すってので、多少は有用性があるし。
((assq obj alist) => cdr)
(連想リストでobjが見つかったら、それに関連付けされた値(cdr)を返す)
0675デフォルトの名無しさんNGNG
>>672
読んだけど、明確には書いて無いじゃん。
”文から察する”のではなくて、はっきりした答えを望んでいたワケよ。
0676デフォルトの名無しさんNGNG
伝統的に1行すつ入力していくということで良い、とも書いてないと思うが?

大体、はっきりした答なんてあるのかね。場合によりけり、では?
0677デフォルトの名無しさんNGNG
>>675
伝統的って何よ
CUIの伝統?
GUIの伝統?
一行入力って事はBASIC?
0678デフォルトの名無しさんNGNG
>>675
脳内までコンピューターになってるぞ。
0679デフォルトの名無しさんNGNG
>>671
フリーで公開されてる処理系のほとんどは対話的な編集機能は
無いみたいです。(DrSchemeとか、IDEが載ってるやつもある。)
標準入力からのダム入力がほとんど。
ただし、そういう場合でもLISPで書かれたコード編集機能とかを提供
していたり、処理系とは別に、LISP用のエディタってのがあるので、
それを使うのが一般的なんでしょう。
LISP専用マシンや、商用のならIDEぐらいは用意してると思います。
0680デフォルトの名無しさんNGNG
つーかemacsあるじゃん
0681デフォルトの名無しさんNGNG
x-emacs
0682デフォルトの名無しさんNGNG
CommonLisp を 6 割くらい実装しているっていう xyzzy もあるし
0683デフォルトの名無しさんNGNG
開発/実行環境は、emacs配下で処理系動かしている人が多いんじゃないかな?
CMU Common Lispなんかは自前のeditor/開発環境が強力だったけど。

>>664はwindowsな人みたいだから、わしにはお勧めが出来ない。
http://www.cs.cmu.edu/afs/cs/project/ai-repository/ai/lang/lisp/impl/0.html
http://www.cs.cmu.edu/afs/cs/project/ai-repository/ai/lang/scheme/impl/0.html
http://SAL.KachinaTech.COM/F/1/
あたりから漁ってみては?
0684デフォルトの名無しさん NGNG
>>674
そんな単純な理由じゃないよ。もしチャンスがあったら John R. Allen の
"ANATOMY OF LISP" を読んでみてください。きっと疑問に思っていることが
かなり解消されると思います。
0685デフォルトの名無しさんNGNG
>>684
これ、結局後半部分の翻訳は出なかったね。
0686デフォルトの名無しさんNGNG
翻訳って出たんだ。改めて読んでみたけど、理論と技術が絶妙なバランスで書か
れていて名著ですね。
0687デフォルトの名無しさんNGNG
>>686
"Let's talk LISP" も名著では?
日本の出版社なら断るであろう絶妙な文章が最高だった.(藁
0688デフォルトの名無しさんNGNG
>>686
大昔。東大後藤研HLISPの人達の翻訳。
日本コンピュータ協会からじゃなかったかな。白とオレンジの表紙。
前半の理論パートだけ翻訳された。

当時実装の情報飢餓だった学生の俺は欝…
0689デフォルトの名無しさんNGNG
あ、もちろん、前半だけでもめちゃ面白かった。
0690デフォルトの名無しさんNGNG
>>688
Lispの実装に興味がなければ前半で十分ですね。理論はこの本で、
実装は K-LISP で勉強させて貰いました。
0691デフォルトの名無しさんNGNG
>>684
Anatomy of LISP は原著&訳書ともに、現在、入手困難だねえ。
神田の古本屋街でも売ってない。若い人は、なかなか読めるチャンスがないでしょ。
マッカーシーのLISP関係の論文を調べる方がよほど楽だもの。
0692デフォルトの名無しさんNGNG
その昔、電総研で国産LISP処理系の実装をしてた人が、
LISPの本質を学ぶには、"LISP 1.5 Programmer's Manual"
で十分だって言ってるよ。その人は、>>633の大学教授。
0693デフォルトの名無しさん01/08/26 18:43ID:N7ZU6aks
>>692
"LISP 1.5 Programmer's Manual" の Eval の定義のページは基本中の基本
ですね。その先に進むとすれば "Anatomy of LISP" なんですよ。
069463901/08/26 18:48ID:N7ZU6aks
「その先」と言っても深さじゃなく幅のことです。
0695デフォルトの名無しさん01/08/27 00:05ID:M6E23zcw
nthcdr って方言によって実装がちがうんですね。

Emacs Lisp では
(nthcdr 2 "a" "b" "c" "d")
→("c" "d")
なのに、Common Lisp を実装しているという YOOL では

(nthcdr 2 "a" "b" "c" "d")
→("d")
になりました。
0696デフォルトの名無しさん01/08/27 00:07ID:M6E23zcw
>>695 のS式間違えました。
(nthcdr 2 '(a b c d))
と読み替えてください。
0697デフォルトの名無しさん01/08/27 02:42ID:HLWIQFE6
>>696
Common Lisp を実装しているという xyzzy では

(nthcdr 2 '(a b c d))
→(c d)

となりました。
0698デフォルトの名無しさん01/08/27 04:08ID:YHyrpXK2
>>695
実装によって機能が異なる関数があっても,それを許容するのが Lisp の
基本的なスタンスです.インプリメンタの解釈が気に食わなければ,関数
を再定義するなり,計算形マクロを定義するなりして,自分の好みにする
ことが可能です.例えば,TAO/ELIS には,MacLisp および ZetaLisp の
互換パッケージがあって,ユーザが趣味(?)の応じて使えるようになって
いました.
# MacLisp は,Macintosh 向けの Lisp の処理系ではありません.(藁
0699デフォルトの名無しさん01/08/28 00:37ID:w0po3FXw
>>684
>そんな単純な理由じゃないよ。
簡単に説明してもらえるとありがたいのですが・・
0700デフォルトの名無しさん01/08/28 22:35ID:eihQBBgU
Common Lisp において、
(setf a '(1 2 3 4 5))
の状態で、list である a の個々の要素に対する操作、一例としては
(max 1 2 3 4 5)
を行う場合、一般的にはどのようにするのでしょうか。
今現在は
(eval (cons 'max a))
としているのですが、これが一般的な書き方なのかわからないのです。
ご教授宜しくお願い致します。
0701デフォルトの名無しさん01/08/28 23:21ID:GcQivBcQ
>>693
なるほど。。。
"Anatomy of LISP"読んでみたいなあ〜。
0702デフォルトの名無しさん01/08/28 23:40ID:VQ.Eh2.o
>>700
(apply #'max a)
0703デフォルトの名無しさん01/08/28 23:54ID:UYkVndh6
Lisper が書いた本を読んだ。
文の内容まで Lisp 風に実装されていた。(汗

「ここではAという概念を説明する。しかし、その前に、Bという概念を説明しておいたほうが望ましいので、まずBを説明する」
「ここではBを説明するが、その前に、Cという概念が必要なので、まずCを説明する」
「Cを説明するがその前にDを...」
てな感じでいつまでたっても本文がでてこない。
いっぺん氏ねとオモタ。
0704デフォルトの名無しさん01/08/29 00:31ID:5V.Ejvn.
Haskell風なら call-by-needで説明できるからいいよ!
0705デフォルトの名無しさん01/08/29 01:28ID:GIhJkjc.
>>703
参考までに本の名前を教えてください。
0706デフォルトの名無しさん01/08/29 01:55ID:GIhJkjc.
>>700
eval/applyを使いたくないなら、maxを2引数固定とみなして、
リストイテレータ(fold-leftとか)を使うとか。
(fold-left #'max (car a) (cdr a))
結局max内部でも同じ様な事してるわけだけど。
070770001/08/29 14:35ID:9ek6n1iU
>>706
現在の問題では 2 引数固定とみなすことはできないので残念ながら
適用できません。
そもそもイテレータという概念がどんなものか理解していないので
これから調べてきます。
ご教授ありがとうございました。

>>702
> (apply #'max a)
キレイさっぱり apply の存在を忘れていました。
ご教授ありがとうございました。

つい最近 Lisp でプログラムを書き始めたのでどうしようもないコー
ドを大量生産中です。
大量に変数を let してしまうし、ついつい副作用を目的とした
function ばかり書いてしまいますし。
速度を求めた場合はそっちの方がよいような気がするのですが、コードが
Lisp らしくなくて自分で泣けてばかりきます。
厨房な質問でスレを汚してしまいすみませんでした。
0708デフォルトの名無しさん01/08/29 22:52ID:KTWH2gm.
schemeならともかく、普通のlispで副作用無しってのはきついんじゃない?>707
0709デフォルトの名無しさん01/08/30 00:03ID:C3TsWUik
>>707
schemeでもLispでも副作用の使い方による。
良い使い方もあるし、悪い使い方もある。
0710デフォルトの名無しさん01/08/30 01:37ID:ewrL03ng
>>707
変数に値を入れるのではなく,値に名前(変数名)を付けるという
考えに頭が切り替われば,副作用は自然に減ると思います.
0711デフォルトの名無しさん01/08/30 12:10ID:OvgrHWKE
コンビネーターってなんですか
0712デフォルトの名無しさん01/08/30 13:55ID:C3TsWUik
>>711
自由変数のないλ式の事。S, K, I, Yなどが有名です。
詳しくは関数型言語スレで。
071370001/08/30 15:35ID:FZu.V9eg
何度もお目汚ししてしまいすみません。
(apply #'max '(1 2 3 5 4))
はうまくいくのですが、
or が defmacro で定義されているため
(apply #'or '(nil nil t nil nil))
(apply 'or '(nil nil t nil nil))
がうまくいきません。
(eval (cons 'or '(nil nil t nil nil)))
で現在は評価しているのですが、'or 等の場合でも常套句がある
のでしょうか。ご教授宜しくお願い致します。

なんだか、Lisp を書いていても list がポインタの集合にしか
見えないっていう余計なワンクッションが頭の中で起こってしまっ
ています。
フィーリングで Lisp を書けるようになるのは遠そうです。

そらから、もし宜しければ、setf と setq の違いについても
ご教授お願いできないでしょうか。
どういう場合にどちらを使うべきなのかがわからず右往左往して
しまっています。
宜しお願い致します。
0714デフォルトの名無しさん01/08/30 22:38ID:36uDa7mk
今日会社の上司に
「今、Lisp の勉強してるんですよ〜」
って逝ったら
「ほえ?リスピュってなに??」
って言われた。
りしゅぴゅって知名度低いって実感した。

ホントは50年の歴史があるんだけどね。
0715デフォルトの名無しさん01/08/30 23:40ID:rGyCxIX.
>>713
CommonLisp第2版の本に、マクロはapplyできないと書いてある筈。
多分普通のifとかの構文も駄目だったと思う。
どうしてもapllyでやりたければ、自分でapplyのラッパーとか
を実装すれば良いんじゃない?
うまいやりかたは知りません。
orの様なマクロや構文であれば、引数をclosureのリストに、
orも相当する機能の関数に置換して、それをapplyする
my-applyマクロを作るとか。
0716デフォルトの名無しさん01/08/30 23:57ID:rGyCxIX.
>>715
setqは単純変数代入文、setfは汎用代入文
普通に使う場合はなにも考えずにsetfで良いと思います。
(インタプリタ上でなんの最適化もせずに実行速度を上げたい
とかの場合以外)
こういう標準的な関数の機能については先程も出てきた、
CommonLisp第2版 著者 GUY L.STEELE JR.(共立出版)
ISBN4-320-02588-1
や、過去ログに載ってるような本を参照してください。
071771601/08/30 23:58ID:rGyCxIX.
>>715じゃなくて>>713
071871601/08/31 00:07ID:Cbba3liI
ここでCommonLispに近い仕様の、ISLISPというISO標準規格の
Lispのリファレンスがweb上で参照できます。(日本語)
ttp://www.ito.ecei.tohoku.ac.jp/~izumi/TISL/doc/ISLISP/index_j.html
トップ
ttp://www.ito.ecei.tohoku.ac.jp/~izumi/TISL/top_j.html
0719デフォルトの名無しさん01/08/31 00:26ID:R3B1Jouc
orがなぜ関数ではなく macroになってるかも考えるべき>>713
多分、関数 or* とか作って applyするのがいいと思うが用途による。
で、 >>715 はなんか違う気がする。
072071101/08/31 01:25ID:qFL5sH4M
>>712
即答ありがとう。逝ってきます。
0721デフォルトの名無しさん01/08/31 01:46ID:JrJLvbeM
>>719
shortcutする必要がなければ、ifで書いた関数でlistをfoldしてもいいしねー。
0722デフォルトの名無しさん01/08/31 01:49ID:.j91wkso
>>713
CommonLispには、orの関数版という感じの
someというのがあるので、それで代用できると思います。
072371501/08/31 01:54ID:.j91wkso
>>713
逆に、andの関数版という感じのはeveryです。

>>719
自分でもややこしいこと書いてしまった感じがします。
0724デフォルトの名無しさん01/08/31 02:01ID:.j91wkso
ちなみにsomoとeveryは述語を指定する必要があるんで、
普通のorやandとして振る舞わせる場合
(defun identity (x) x)
とでもして、
(some #'identity 〜)
(every #'identity 〜)
として使ってください。
(もっと適切な関数があるかもしれませんが。)
0725デフォルトの名無しさん01/08/31 02:23ID:oLrxQ0UE
>>713
リストの中身を評価する必要がなければ、、
(find-if #'identity '(nil nil t nil nil)) や
(member-if #'identity '(nil nil t nil nil)) などで
代用できる。評価するのなら、evalでいいんじゃないかな。
0726デフォルトの名無しさん01/08/31 02:29ID:oLrxQ0UE
>>724
identityは標準であるよ。
072771301/08/31 15:59ID:H3ikKes.
>>715 >>719 >>721 >>722 >>723 >>724 >>725 >>726
親切に回答してくださりありがとうございます。
リストの中身を評価する必要があるため、今回は
(some #'identity 〜)
でいこうかと思います。
ありがとうございました。

>>716
基本的なことにもかかわらずご返答してくださりありがとうございました。
KCL の実装上での CommonLisp についての解説がかかれた
「CommonLisp 入門」をようやく読める環境になったので、今後このような
質問はしないよう、基本をきちんと学ぼうと思います。

>>719
> orがなぜ関数ではなく macroになってるかも考えるべき>>713
実はまだ自分で defmacro でマクロを定義したことがないため macro の有用性
についてきちんと把握できていない状態です。
「CommonLisp 入門」を読んで勉強してきます。

皆様、ご返答ありがとうございました。
0728デフォルトの名無しさん01/09/01 01:54ID:ctDE.PS.
LISPっていうと、コモンの話題ばかりになってしまう風潮が気に入らない。
コモンの話題しか話せない様なのは、真のLISPerじゃない!
コモンの様な軟派な亜流のLISPじゃなく、無駄な機能を省いた、美しいLISP言語
の真髄に関する話題を希望。
そもそも、コモンLISPだあ、オブジェクト指向だあって言ってる連中は、
LISPの処理系の内部の詳細を知って、自分で処理系を作る能力があるのだろうか。
真のLISPerなら、処理系を自分で実装してみるべき。
>>708
LISPで副作用のない、副作用のない関数型プログラミングができてこそ、
真のLISPer
0729パンティーはいたまま排便、好きな人01/09/01 01:59ID:OK9pI4Co

パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
パンティーはいたまま排便、好きな人
0730デフォルトの名無しさん01/09/01 19:43ID:Wnumu9r2
>>728
Scheme
0731デフォルトの名無しさん01/09/01 21:21ID:loW1WFjk
えーなんでー。
歴史的には
Lisp → すきぃむ → こもんLisp
だから、顧問LIsp が最強なんでしょ?

すきぃむ って OO 対応してるの?
0732デフォルトの名無しさん01/09/01 23:01ID:Hclu0oRE
Guile=Scheme
0733デフォルトの名無しさん01/09/01 23:22ID:cxkeoCoY
>>731
Schemeは今現在も発展してるし、
OOも対応してる
0734デフォルトの名無しさん01/09/02 01:25ID:.7XrLN8.
>>731
コモンが最強だというのは、コモン信奉者の妄想。
あんな言語仕様が水膨れしたものを平然と使う神経が理解しがたい。
731はLISPの何たるかを全く理解しないまま、世間のいうことをそのまま鵜呑みに
してるだけ。
0735デフォルトの名無しさん01/09/02 01:38ID:.7XrLN8.
10年くらい前までは、LISPの処理系の実装に関する書籍が、洋書和書
を問わずに何冊か出てたけど、最近は全くないなあ。
今じゃあ、LISP言語自体の解説書も良書と呼べるものは、殆ど出て
ないし(SICP及びその訳書は別として)。
こんなんじゃ、真のLISPerは育たんよ。
0736デフォルトの名無しさん01/09/02 12:11ID:/QCPLR4U
http://www.recruit.co.jp/cgi-bin/rperl5.pl/r-staffing/search/search.html?AREA=1

↑ここの
「プログラミングスキルをいかせるお仕事」
UNIX UNIX−C C++ VC++ COBOL
PL/1 VB Java JavaScript Linux
Oracle SQL Perl

Lisp は入ってないねぇ。
0737デフォルトの名無しさん01/09/02 13:13ID:ulMTJ1N.
>733
OOも対応してるって、「規格で」ですか?
実装で対応してるっていうのはよく見かけるけど……。
0738デフォルトの名無しさん01/09/03 02:37ID:LXi6Pi92
>>737
規格というか、「暗黙に」では?
メッセージパッシングやデータ主導とか。
マクロが構文として書けるので、OOの対応レベルやインタフェースを
自分で決定できる。既存のOOパッケージを使用するという方法が楽かも。
(ちなみにCommonLispのCLOSとかもマクロとして実装できる。)
速度が問題では無いときには、コアを小さくしておいて
他の構文やらは全部マクロで定義、とかはLISPではよくあります。
関数型として書けば別にOOは必要ないと思うけど。
0739デフォルトの名無しさん01/09/03 02:39ID:LXi6Pi92
>>736
LISPコードをそのまま納品する仕事ってのは
確かに少ないかもね。
0740デフォルトの名無しさん01/09/03 05:19ID:hl5nRbHk
誰か本書けや
0741:デフォルトの名無しさん01/09/03 13:57ID:FtmBGRGU
>>731
歴史的経緯をちゃんと見れば「理論的には」Schemeが最強だね。
0742デフォルトの名無しさん01/09/03 21:38ID:qXV4pYUY
>>740
今、日本にオリジナルの良書を書けるほどのツワ者LISPerが何人いることか。。。
電通大の竹内先生とか、SICPを翻訳した和田先生、東大の萩谷先生に京大の湯浅先生
とかくらいかな。
0743デフォルトの名無しさん01/09/03 21:44ID:wy3QSGS6
萩谷・湯浅の本とか、訳書とかなら大きな本屋に売ってるでしょ。
図書館行けば間違いなく置いてあるし。大学生有利かな。
0744デフォルトの名無しさん01/09/03 21:45ID:qXV4pYUY
>>741
Schemeは、確かに無駄な機能を極力省き、数学的に美しい。
だけど、何をもってして最強と定義するのか、それが問題。
記号処理を主体とした汎用プログラミング言語として、必要
十分条件を満たす言語を最強と定義するなら、Schemeはどうかな?
少なくとも、この定義なら、コモンは十分条件は満たすけど、必要条件
ではなく、無駄な部分が多いので、最強ではないね。
個人的には、LISP 1.5がいいと思うけど。
0745NIL01/09/03 21:49ID:o032XSFY
某訳書は酷い翻訳だったけど,原書の装丁がそれよりも酷かっ
た(3日使うとバラバラになった)ので売れたんだよねぇー.
0746デフォルトの名無しさん01/09/03 21:53ID:qXV4pYUY
>>743
湯浅先生は、最近はLISP系の本を書いてないね。
HPではJAVAでSCHEMEの実装とかを公開してるけど。
萩谷先生は、日本評論社から「関数プログラミング」って本を
出したっしょ。これは初学者にはわかりやすくてお奨めだけど、
上級者には物足りないかも。
0747デフォルトの名無しさん 01/09/03 21:53ID:o032XSFY
>>744
LISP1.5はシンプルだけどFSUBRという盲腸があるからな...
0748デフォルトの名無しさん01/09/03 21:55ID:qXV4pYUY
>>745
某訳書って?
0749デフォルトの名無しさん01/09/03 21:58ID:qXV4pYUY
>>747
確かに、一理ありますな。
この定義を満たす言語ってのが難しいから、いろんな方言が出てきたの
だし。
0750デフォルトの名無しさん01/09/03 22:04ID:U9hn1Usc
Schemeの多値を返すインターフェースの部分って
規格書(R5RS)みた限りではなんだか中途半端な気がしますが、
実際どうなんでしょう。使ってる人っていますか?
valuesやcall-with-valuesの辺り。
0751デフォルトの名無しさん01/09/03 22:06ID:qXV4pYUY
>>745
今、書棚のLISP本コレクションを眺めながら思ったけど、
某訳書って、まさか、後○先生が翻訳した、アノ本じゃあないよねえ。。。
0752デフォルトの名無しさん01/09/03 22:11ID:qXV4pYUY
>>750
R5RSで曖昧な定義になっているのは、処理系によって微妙に違う
ことがよくある。私が一番信頼している(信頼できると思う)のは、
MIT Schemeの実装だけど。
0753デフォルトの名無しさん01/09/03 22:18ID:7MZMrdcY
>>751

SICP じゃないの? ゼミの学生が訳したとしか思えんかったが。
Web で原文が公開されてることが分かってたら買わんかったのに。
訳はともかく内容は期待通りすばらしかった。
0754デフォルトの名無しさん01/09/03 22:21ID:qXV4pYUY
>>753
SICPって言っても、初版の方のことでしょ?
二版は、和田先生が翻訳してるから、しっかりしてるはず。
(訳本も買ったけど、原書しか読んでないので、確かじゃないけど。)
0755デフォルトの名無しさん01/09/03 22:23ID:qXV4pYUY
>>753
SICPの初版の装丁って貧弱だったかな?
二版の装丁はしっかりしてるけど。
0756デフォルトの名無しさん01/09/03 22:28ID:xBWWifTI
>>750
ああインタプリタの実装のときすごく困った。
結局本体に手を入れたような。
0757デフォルトの名無しさん01/09/03 22:31ID:o032XSFY
LISPファミリーに於ては、規格書は『メーカー希望小売価格』のよう
なもので、それが絶対的なものではありません。それがLISPの良さの
1つなんですが、残念ながら嫌われたり批判されたりする理由にもな
っています。個人的には道具としてのTAO/Heliumが好きでした。
0758デフォルトの名無しさん01/09/03 23:05ID:7MZMrdcY
>>754

あっ二版の方です。
どうなんだろ、みんなはそうでもないんかな。
どうも某訳というのは SICP じゃさなそうだけど。
0759デフォルトの名無しさん01/09/03 23:09ID:7MZMrdcY
>>758
じゃなそう => じゃなさそう
0760デフォルトの名無しさん01/09/03 23:40ID:1zSk4pr2
LISPは仕様変更/拡張されてもある程度までなら自力で修正が
効くからあんま困らないね。
(多値対応は恐らく処理系自体に対して修正が必要だけど)
0761デフォルトの名無しさん01/09/04 08:46ID:YviMCw/Q
Lisp系の言語でどれが最強かという話ならDylanはどうなるかな?
括弧が無い書き方も出来るから拒否感がある人もいるかもしれないけど、
Schemeを発展させたような仕様らしいよ。

Haskellなども候補になると思うけど、これはスレ違い。
0762デフォルトの名無しさん01/09/04 11:30ID:5Y4kUfsc
>>761
Apple が初期に作ってたころは括弧ついてたけど、その内なくなった。
今のは括弧を受けつけないんでは。

現在、実装が行われているのはこれか。
ttp://www.gwydiondylan.org/

下の Larry Tesler の前書きを読むと Scheme を発展させているようには思
えんけど。 CLOS の影響を受けているようだが。

ttp://www02.so-net.ne.jp/~komuro/Mutsumi/DylanInfo/foreword.html
0763デフォルトの名無しさん01/09/04 17:11ID:CUE4BAnw
>>762
でもLispに多大な影響を受けてるのなら、Schemeもたくさん参考にしたのは
間違いないと思うよ。
0764デフォルトの名無しさん01/09/05 02:48ID:jFtajofc
>>761
SchemeでDylanをエミュるの無かったっけ?
0765デフォルトの名無しさん01/09/05 03:09ID:jFtajofc
検索したら見つかった。
Bob: Jim Miller's algolesque syntax for Dylan implemented in Scheme.
http://www.cs.cmu.edu/afs/cs/project/ai-repository/ai/lang/scheme/code/syntax/bob/0.html
0766デフォルトの名無しさん01/09/05 22:52ID:1ojJgpEE
bobdylan
0767デフォルトの名無しさん01/09/06 01:42ID:d8b4MtxQ
こっちに貼っておきます。
The Hotdog Compiler
(Scheme->JVM
Scheme->C
Scheme->.NET)
http://www.cs.nwu.edu/~surana/
BaseがScheme48かな?
0768デフォルトの名無しさん01/09/06 03:51ID:9dUi5gVA
こもんりすぷ、は、列とかをCLOS風に直さないかね。
この際、assocも多値にして。setfが可哀想…
0769デフォルトの名無しさんNGNG
なんかschemeのソース見てると、
(null? #f)
=>#t
を前提としてるコードがよくあるんだけど、
これってどういう事なのかなあ?
(null? '())
=>#t
これ以外は#fが返る筈だと思ってたんだけど。
具体的なやつは、例えばassoc/member系の失敗判定をnull?で行なってたり。
0770デフォルトの名無しさんNGNG
>765
これってMIT-Scheme用だね。
char-setとか非標準なやつ使ってる
0771デフォルトの名無しさんNGNG
>>754
第2版にしてみても読みにくいと思うけど。
原文も難しいの?
0772デフォルトの名無しさんNGNG
lispのnilがschemeでは#fに相当するからでは?>769
0773デフォルトの名無しさんNGNG
>>772
相当しません。lispのnilは、schemeでは#fとnilに分解されました。
(null? #f)
=>#f
です。
0774デフォルトの名無しさんNGNG
そういえばschemeの、'() #fや#tなどのcar cdrって、
取ってよい物なの?
ぶっちゃげた話、
(car #f)
=>#f
とかは成り立ちますか?
0775デフォルトの名無しさんNGNG
>>774
成り立つ筈
(car '())
=> ()
0776デフォルトの名無しさんNGNG
>>769
たしかR4RS以前は、#fと'()(nil)を同一視してたと思う。
0777デフォルトの名無しさんNGNG
schemeにもnamespaceが欲しい
(genericな実装をするときに困る)
自力でできないことは無いけど
標準化されてるに超したことないし
0778デフォルトの名無しさんNGNG
改行を含む文字列をCommon Lispでどうやってかくの?
リテラルで。。(リテラルとはいわないみたいだけど)

へたれな質問ですんまそ。。へたれsage。
0779デフォルトの名無しさんNGNG
>>778
文字なら
#\returnまたは#\newline
文字列はそのまま改行するんでは?
"改行を含む文
字列"
0780デフォルトの名無しさんNGNG
>>779
エエッ!?そのままでいいの??
ACLのコンソールでうまくいかなかったからあきらめてた。。
欝だ。。'(good-bye world)

恥さらし:
(format nil " ~C )" #\Newline)

ありがとう。。
0781デフォルトの名無しさんNGNG
SchemeのOOパッケージってtiny-closとstklosの
他に何かありますか?(stklosのベースはtiny-closみたいだけど)
0782デフォルトの名無しさんNGNG
http://srfi.schemers.org/srfi-20/srfi-20.html
0783デフォルトの名無しさんNGNG
http://www.cs.indiana.edu/scheme-repository/code.oop.html
http://www.cs.cmu.edu/afs/cs/project/ai-repository/ai/lang/scheme/oop/0.html
0784デフォルトの名無しさんNGNG
最初はBOSというOOパッケージが
軽いしシンプルで良いと思う
0785デフォルトの名無しさんNGNG
やっぱlispだとCLOS風の
(method obj args...)
という呼出し形式が一般的なんですか?
(obj method args)
だとapplyとかが使えなくなるから?
0786デフォルトの名無しさんNGNG
>>785
Lispでは昔からfunctionとoperatorを区別しない習慣だけど、
そうすると+のようなbinary operatorは、(Lispではn-ary operatorだけど…)
(method obj args...)とか(obj method args...)とかいう見方は不自然だわな。
どうしても(method obj1 obj2)となる。で、generic functionの世界へ突入。

C++もoperator overload, generic functionがあるね、
だから、send message to objectの世界からは少し離れている。

Smalltalkみたいに一つの見方で閉じてるのが特殊なんだと思う。
0787デフォルトの名無しさんNGNG
>>785
CLOS形式の利点は既存の関数がそのまま使える点にあると思う。
(メソッドと関数を区別する必要が無い)
0788デフォルトの名無しさんNGNG
(method obj1 obj2)
ってやると、どっちのobjectのmethodが立ち上がるのでしょうか?
obj1ですか?
0789デフォルトの名無しさんNGNG
>>788
obj1が<class-1>か、<class-1>の関係クラス
obj2が<class-2>か、<class-2>の関係クラス
として、
(method <class-1> <class-1>)
という形式のmethodが呼ばれる。
どっち、っていうのは考えない方が良いとおもう
主従関係があるとすれば、obj1の方。
0790デフォルトの名無しさんNGNG
(method <class-1> <class-2>)
でした
0791デフォルトの名無しさんNGNG
>>788
>>789のとおりだけど。。

第一引数(いわゆるthis、self)に対して特別なアクセス権を有する、
なんていう区別がないから、メソッドの引数はみんな平等だよ。

「メソッドは引数の型によって総称関数から選択される手続きである」
(引用元:ウィンストンとホーンの『LISP 原書第3版 (I)』培風館)

総称関数(generic function)ってのは同じ名前のメソッドの集まり。
だから「メソッドは総称関数に属している」のほうがぴったり。
0792デフォルトの名無しさんNGNG
>>784の言うBOSって
(method obj . args)って形式しか
dispatchしないみたいなんですけど、
これを例えば
(method obj1 obj2)
と書きたい時はどうするんでしょう?
(第2引数以降の型も区別させたい)
良い方法ありますか?
0793792NGNG
総称関数内で、argsに対してis-a?判定するしか
ないでしょうか?2度手間な気がします。
0794デフォルトの名無しさんNGNG
>>792
良い方法は思い付かない。
多分、書き換えるしかない気が・・
ソース見た感じでは、
(assq generic specialised-methods)の辺りを
第2引数以降も判定する様に書き換えればなんとかなりそうだけど。
0795デフォルトの名無しさんNGNG
その場合、最も限定的なmethodからヒットする様に
specialise!される度に、methodを引数についてソートする。

あとは総称関数の登録インターフェースに↓みたいな形式を許可する。
(specialise! add (list <number> <number>)
(lambda (call-next-method l r) (+ l r) ))
0796デフォルトの名無しさんNGNG
いっそのことマクロで↓みたいにするとか。
(defmethod add ((l <number>) (r <number>)) (+ l r))

つーか、tiny-clos辺りに乗り換えては?
(実装が3倍ぐらい大きいけど)
0797デフォルトの名無しさんNGNG
あと考えられるのは、
↓の様な、明示的型変換を行なう総称関数を作って、
(define-generic ->number)

+に渡る型を<number>のみになる様にフィルタリングするとか。
(specialise! add <number>
 (lambda (call-next-method obj . args)
  (apply + (cons obj (map ->number args)))))

解決にはなってないけど。
0798792NGNG
色々参考になりました >>794-797
なんとか修正できそうです。
BOSは小さい割に完成されている感じがするので
しばらく使ってみようと思います。
0799デフォルトの名無しさんNGNG
multi-methodをsupportしてない言語で使われる
double dispatchと呼ばれるpatternだから、検索してみれ
0800792NGNG
なんとか形になりました。
(ドット対の部分がまだしっくりきませんが)

>>799
visitorパターンの事ですか?
(define-method method1 ((obj <class1>) arg)
 (method2 arg obj)) ;method2に処理を委譲

(define-method method2 ((obj <class2>) arg)
 (実際の処理 obj arg) )
という感じになるんでしょうか。
0801デフォルトの名無しさんNGNG
dylanの書式と似てるね
0802792NGNG
結局こういう風に記述できる様にしました。
(define-method method1 <class1>
 body) ;<class1>の参照はselfで行なう
または
(define-method method1
 (obj <class1> . args) body)
または
(define-method method1
 ((obj1 <class1>) (obj2 <class2>) . args)
 body)
お答え下さった方々、ありがとうございました。
0803デフォルトの名無しさんNGNG
MOPが付いてるぶん、tiny-closが良い感じだけど、
そのまま使うにはちょっと重い気がする
0804デフォルトの名無しさんNGNG
>>803
メソッドディスパッチは適応させるメソッドが多くなると遅くなるから、
レキシカルに固定化されたコードを解析して、実効メソッドに変換する
処理ってのが必要になると思う。
0805デフォルトの名無しさんNGNG
簡単な最適化は、メソッド初回起動時に引数を解析して、
適応する可能性のあるメソッドのみを選択するclosureを作成して
次回からはそれを呼び出す様にする、とか。(メモ化)
これだとコードの探索は必要無い。
この処理をマクロ化して、コードをmacro-expandしておけば、
初回の解析も省かれる。
0806デフォルトの名無しさんNGNG
普通の呼出し
(lambda (args)
 ((find-method args) args))
↓
メモ化
(letrec ((method
 (lambda (args)
  (set! method (find-method args))
  (method args))))
 method)
0807デフォルトの名無しさんNGNG
Inter Lisp って普通の Lisp とどっか違うんでしょうか?
0808いつでもどこでも名無しさんNGNG
「普通のLisp」の意味を知りたいな...
0809デフォルトの名無しさんNGNG
ACLと普通のLispと(以下略)
0810デフォルトの名無しさんNGNG
メモ化って、適用するコードを書き換えないでできるでしょうか?
例えば下のfibについて(add dec == が総称関数だとして)

(define (fib n)
 (let loop ((a 1) (b 0) (c n))
  (if (== c 0)
    b
    (loop (add a b) a (dec c)))))

自分が思い付いたのは、
(define (fib n)
 (with-memorize-method (add dec ==)
  (let loop ((a 1) (b 0) (c n))
   (if (== c 0)
     b
     (loop (add a b) a (dec c))))))

こういう風にループ前にメモ化を明示する方法なんですが。
(上の様にfibをメモ化すると、4倍程速くなりました。)
0811デフォルトの名無しさんNGNG
>>810
ディスパッチ処理でキャッシュしてみては?
関数に渡された引数の数や、引数の型同士のeq?比較の様な軽い
判定で、まずキャッシュにヒットするかをテストしてみる。
0812デフォルトの名無しさんNGNG
つーか、BOSのメソッド探索アルゴリズムって、
まだ改善の余地ありって感じだけど
0813デフォルトの名無しさんNGNG
機能追加はlispの十八番
VisualLISP
せめてTurboLISP作ってくれyo!
0814デフォルトの名無しさんNGNG
>>808>>809
そのツッコミで大体分かりました。ありがとう。
0815デフォルトの名無しさんNGNG
>>808
LISP1.5
0816デフォルトの名無しさんNGNG
C->LISPのトランスレーターってありますか?
0817デフォルトの名無しさんNGNG
LISPでOOってのも良いかもね。
余計な構文いらないし
0818デフォルトの名無しさんNGNG
(・∀・)
=>イイ!
0819デフォルトの名無しさんNGNG
(define (・∀・)
 (lambda x (if (pair? x) (list 'カエレ! x) 'イイ!)))

((・∀・))
=>イイ!

((・∀・) >>818)
=>(カエレ! >>818)
0820デフォルトの名無しさんNGNG
s/list/list*/(・∀・)デシタ!
0821デフォルトの名無しさんNGNG
((´ ∀`) >>818 - >>820)
0822デフォルトの名無しさんNGNG
>>818-821
( ゚Д゚)
=>逝って良し!
0823デフォルトの名無しさんNGNG
>>816
CTAXというのがあった様な・・?
0824デフォルトの名無しさんNGNG
>>816
たしか
dylan->lisp/scheme
tk->lisp/scheme
logo->lisp/scheme
というのがあるから、その辺を参考にするとか。
(Cのパーサーってのはあったと思う。)

lisp/scheme->C
なら沢山あるんだけどねぇ
>>823
ctaxはC風の構文トランスレーター(guile)
0825792 810NGNG
>>811-812
あれから、メソッド毎に枝分けする様に変えてみたら多少速くなりました。
普通の関数にはまだ及びませんが。
キャッシュする方法を考えてみます。
0826デフォルトの名無しさんNGNG
自分でリストを表示するルーチンを作ってるのですが、
リストが巡回構造だと判定する良い方法はありますか?
0827デフォルトの名無しさんNGNG
親を順番に検索していって自身が検索されたら巡回
0828デフォルトの名無しさんNGNG
>>827
やっぱりそういう地道な方法しかないですか。
ありがとうございました
0829デフォルトの名無しさんNGNG
探索の手間が惜しいなら、リミッタを付けるとかすれば?>828
0830デフォルトの名無しさんNGNG
(let ((x (list 'dmy)))
 (set-car! x x)
 (set-cdr! x x)
 x)
=>(((((((((((((((((((((((((((((((((((((((((((((((...
0831デフォルトの名無しさんNGNG
>>829
表示だけならそれで良かったですね。
0832デフォルトの名無しさんNGNG
Schemeてどう発音するんですか?
聞く人によって答えが違う…
0833デフォルトの名無しさんNGNG
すきいむ
0834デフォルトの名無しさんNGNG
http://eiwa.excite.co.jp/sounds/NEW_EJJE/000897200040.wav
0835 NGNG
"scheme"のアクセントは「スキー」と同じみたいだけど、
言語のことをいうときはアクセントなしで読んでるなあ。
0836デフォルトの名無しさんNGNG
>>826
仕事と同時にcheck。

(defun search (x l)
"lの中にxがあったら、それがcarなlistを返す。なければnil。"
(cond (((null l) nil)
(eq x (car l)) l)
(t (search-1 x (cdr l) l))))

(defun search-1 (x l r)
"searchの下請け"
(cond ((eq r l) nil) ; loop break
((null l) nil)
((eq x (car l)) l)
(t (search-1 x l r))))
0837デフォルトの名無しさんNGNG
schemeの関数にデフォルト値って置けないですか?
CommonLISPのoptionの様な事したいんですけど
0838デフォルトの名無しさんNGNG
>>837
(define (func . args)
(if (null? args)
(display "hello world!")
(display (car args)))
(newline))

(func)
hello world!
(func 'hoge)
hoge
0839デフォルトの名無しさんNGNG
lisp って意外と簡単でおもしろいね。
今まで見にくいとか差別してすいませんでした。
0840デフォルトの名無しさんNGNG
記念age
0841デフォルトの名無しさんNGNG
>>838
いえ、そういう事じゃなくて、
(define (f x :option (y 1) (z 2))
 (+ x y z))
で、
(f 0)
=>3
(f 0 0)
=>2
(f 0 0 0)
=>0
というのをしたかったんです。
マクロでできるかな?
0842shigeNGNG
(quit)
0843デフォルトの名無しさんNGNG
>>841
マクロでちょっとしたパーサを書けばなんとかなる
0844デフォルトの名無しさんNGNG
>>841

(define f (lambda (x :option (y 1) (z 2)) ...))
という書き方もしたい場合、lambdaも加工する必要がある。
どちらにせよ普通に考えれば、引数の使われかたを実行時に
判定する関数になるかと。
展開コードの例
(define (f x . rest)
 (let ((len (length rest)))
  (let ((y (if (> len 0) (list-ref rest 0) 1))
     (z (if (> len 1) (list-ref rest 1) 2)))
   (+ x y z))))
マクロを生成するマクロにすれば、実行時判定は消えるけど、
関数引数やapplyで呼び出せないなどの制限がある。
0845デフォルトの名無しさんNGNG
前、どっかにoption使う例があったと思った。schemeで。
多分マクロ
0846デフォルトの名無しさんNGNG
>>841
syntax-rulesで、lambda-with-optionってのをdefineして、

(define f (lambda-with-option (x :option (y 1) (z 2)) 略)

ってやれば?

# defineの第一引数がpair?なら…ってダサクない?
# (a b c)って形式の意味を定義する、ってノリなんだとは思うけど。
0847デフォルトの名無しさんNGNG
>>846
># defineの第一引数がpair?なら…ってダサクない?
(define (a b c) ...)は確実に記述量とカッコのネストが
減るからsyntax-sugarとしては妥当かと
0848デフォルトの名無しさんNGNG
>>841
http://zowie.metnet.navy.mil/~oleg/ftp/Scheme/parsing.html
ここのinput-parse.scm の中に

(define-opt (foo arg1 arg2 (optional (arg3 init3) (arg4 init4))) body)
という形式を変換するマクロがあったよ。
0849デフォルトの名無しさんNGNG
>>847
define-functionとか別の名前にして欲しかったなー。
二つ意味を持つのは美しくない。
0850デフォルトの名無しさんNGNG
美しくない?
0851デフォルトの名無しさんNGNG
気に入らなければ各自
構文を拡張せよ
0852デフォルトの名無しさんNGNG
>>849
考え方、オカシイヨ
0853デフォルトの名無しさんNGNG
(define (f))は
(define f (lambda ()))
でしょ?
(define a 1)とするのと変わらない。
2つの意味って何のこと?
0854デフォルトの名無しさんNGNG
$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$

あなた達には分からないでしょうが、Rubyは素晴らしい言語です。
オブジェクト指向スクリプト言語として他のスクリプト言語を圧倒する性能と美しい言語仕様を持っています。
例えば、SchemeやSmallTalkなどは比較的美しい言語だと言われていますが、後発である優位さでRubyは
さらなる美しさと実用性を備えています。
もちろんPerlやPythonなど問題外です。
日本語との親和性ではRubyしか選択肢がないでしょう。

LinuxのディストリビューションもRubyの採用例が増えてきています。
1年後には全てのディストリビューションがRubyを標準採用するでしょう。
Rubyは未来のスクリプト言語なのです。

長くなりましたが、コピペではありません。
賛同していただける方はRubyの事を分かっていただけない人に出会ったら、
この発言をコピペしていただければ幸いです。
0855デフォルトの名無しさんNGNG
>>854
早速Delギコスレにコピペされていましたよ。よかったですね。
0856デフォルトの名無しさんNGNG
Rubyはクソです。ゴミ箱逝きです。

いじょ
0857デフォルトの名無しさんNGNG
Smalltalk氏「Rubyはカッコがオブジェクトじゃない。全てが
オブジェクト?笑わせないでくれ。(プ」

Scheme氏「Rubyはプログラムや継続自体がファーストクラスオブジェクト
ではない。文字列をeval?リストじゃないの?(ワラ」

Perl氏「Rubyが綺麗だって?endの羅列で汚いじゃん。(ゲラゲラ」
0858デフォルトの名無しさんNGNG
Perlに汚いって言われるなんて、言語として最大の屈辱だよな(藁
0859デフォルトの名無しさんNGNG
でも事実だから仕方ないよ。
0860デフォルトの名無しさんNGNG
ダメ人間共がRubyを煽ってるねー。
そんな事をして楽しいのかなあ。
857なんて全然わかってないし(藁
実用性ならRuby>>>>>>>>>>>>>>>>>>>>Smalltalk,Schemeだよね。
今時SmallTalkやSchemeで何作れっていうの?(プププ
0861デフォルトの名無しさんNGNG
>>854-860
きみらスレ違いなのヨ
0862デフォルトの名無しさんNGNG
しかしワラタ
08631RubyユーザNGNG
Schemeなんかに実用性はありません。いじょ
0864デフォルトの名無しさんNGNG
>>863
ハァ?
schemeで検索してみたら?
実用例が山ほど出てくるから。
0865デフォルトの名無しさんNGNG
>864
君はscheme何に使ってんの?
0866デフォルトの名無しさんNGNG
りかぁじょん のおべんきょう。
0867デフォルトの名無しさんNGNG
googleで検索してみた所
Scheme 約5,010,000件
Ruby 約1,630,000件

レベルが違うんだよ、厨房君。
0868デフォルトの名無しさんNGNG
schemeってDBとかいじれるの?
Rubyはいじれますよ。
Ruby/TKって知ってます?
schemeはGUIプログラミングなんて出来ないでしょ。
08691Rubyユーザ NGNG
ね。おもしろいでしょ。
ちょっと扇ってやっただけでこの反応。
マイナー言語ユーザの結束の固さ(大爆笑)には毎度ながら驚くよ。(嘲笑)
0870デフォルトの名無しさんNGNG
866=867なんかに実用性はありません。いじょ
0871デフォルトの名無しさんNGNG
Rubyに実用性で負けているのは事実です。
ですが、わざわざここに来て書き込む事ではないでしょう。
Rubyスレッドに戻ってください。
0872デフォルトの名無しさんNGNG
868みたいなのはRuby使ってもScheme使っても
「DB」なんていじれないし、「GUIプログラミング」とやらもできないだろうな。
0873デフォルトの名無しさんNGNG
なんだ?
なんでruby厨房がこんなところに?
0874デフォルトの名無しさんNGNG
>>848
そのサイトってなんか色々あるね
0875まじれっさNGNG
>>867
scheme も ruby も、他に意味を持った単語なんだから
検索して出てくるものすべてが、プログラミング言語である scheme や ruby
を指しているわけじゃないので、それってちょっと意味無いと思うよ。
0876rubyNGNG
sage
0877デフォルトの名無しさんNGNG
schemeって名前カコイイ
0878デフォルトの名無しさんNGNG
ったら鞭打
0879デフォルトの名無しさんNGNG
よーし、1000目指すぞ!
0880デフォルトの名無しさんNGNG
LISPでマクロを作るという意味がやっとわかった。
ほとんど新しい構文じゃん
0881所新車NGNG
最近、SICPを読み始めて、その流れでMIT Schemeを使っているのですが、
みなさんの使っているLisp処理系はどういうものなんでしょうか?

少しでも調べてみると、Lisp処理系は異常なほどにべらぼうに多いので
どういうものがポピュラーなのか、初心者向けなのか、遊びがいがあるか…
というのが、よく分からないです
最近、DrSchemeを使い始めましたが、これは楽しいですね
0882 NGNG
♪Girls just wanna defun

I can't wake up, in the morning
Cause of what I've been doing for most of the night.
Teacher don't you know my program is done?
And girls just wanna defun.

The phone rings, in the middle of the night
Advisor screams, "Watcha gonna do with your life?"
Patrick**, how I relish double-oh-one***!
And girls just wanna defun.

They just wanna, just wanna, yeah
Girls just wanna defun.

Some people say
A beautiful girl can't tool all night like
The rest of the world.
I wanna be the one to welcome the sun.
And girls just wanna defun.
0883デフォルトの名無しさんNGNG
>>881 自作しろ
0884 NGNG
>>881
いちばんメジャーなのはSCMじゃないの。
0885デフォルトの名無しさんNGNG
SCMとGuileって何が違う?
0886デフォルトの名無しさんNGNG
guileとSchemeとのもっとも大きな違いは、guile では識別子とシンボルで大文字と小文字が区別される点です。
これは大文 字と小文字を区別する他の言語とのインタフェースをとりやすくするため と考えられます。
変数や定数に一貫した名前を使っていれば、 Schemeプログラムはguileでも動作します。
guileではTk、gimp、gtkなどのGUIをモジュール として取り込んで利用したり、逆に異なるアプリケーションから guileオブジェクトを利用することが容易になっています。
guileのベースになったのはAubrey Jafferさんの SCM(version 4e1)ですが、SCMとはだいぶ違ったものになっ ています。SCMの軽快さはguileでは当初から失われていました。
Schemeの拡張と見るか肥大化と見るかによって、guileの 評価は変わるでしょう。guile自体はいずれの評価とも関わりなく、 活動と拡大を活発に続けています。

http://www4.ocn.ne.jp/~inukai/scheme_j.html
0887デフォルトの名無しさんNGNG
slibというものを落としてみましたがどういうものかさっぱり分かりません。
0888デフォルトの名無しさんNGNG
>>887
じゃあなんで落としたの?
0889887NGNG
>>888
ポケットに穴が空いていたんです。
0890デフォルトの名無しさんNGNG
(  ´_ゝ`)  < ふーん
0891デフォルトの名無しさんNGNG
Bigloo
ってどうでしょう?
0892デフォルトの名無しさんNGNG
使ってみろよ
0893デフォルトの名無しさんNGNG
guile-for-winがあれば便利なのだが
Tkは、使いたくない
0894デフォルトの名無しさんNGNG
>>841
亀レスだけど。
(lam (<a1>... [&optional <o1>...] [&rest <r>]) <body>)
こういう構文が書けるらしい。
http://www-2.cs.cmu.edu/afs/cs/project/ai-repository/ai/lang/scheme/code/ext/function/
0895デフォルトの名無しさんNGNG
なんでもありだな
0896デフォルトの名無しさんNGNG
LISPの欠点は区切りが空白しか無いこと。
(+1 2)
これは'+1'というシンボルを探しに行く。

(with-operator (+)
(+1 2))
こういうのが欲しい。可能?
0897デフォルトの名無しさんNGNG
>>896
どうしてわざわざくっつけたいの?
0898デフォルトの名無しさんNGNG
>896
マクロでできる。
本気で考えてるなら、リーダーを自分で作るとかした方が良い。
0899デフォルトの名無しさんNGNG
>>898
できたとしても、適用できる範囲が狭そうだから無駄な労力に
なるかも・・・
0900デフォルトの名無しさんNGNG
\\\     \ \\
   \\ヾ__ ∧_∧_ヾ\
\   \ \ (*´∀`)_\ \
\\     | ̄ ̄∧∧  |  ヾ
\\\ ヾ   |\ ミ;゚Д゚ ∧_∧
  \\\      | ̄ ̄ ( *・∀・) 今だ!900番ゲットォォォォ!!!
   \\\ ヾ  |\ ̄/っ y っ\
     \\       |  ̄ ̄ ̄ ̄ ̄ |
0901デフォNGNG
SICPをチョット前から読み始めて、同時にSchemeも始めたのですが…
今更になって、今まで使ってたS式自体がリストだって事に気づいた
すごいね…の一言

SICPでは、継続とかマクロとか出てこないみたいなんですけど、
知ったら、やっぱり、すごいと感じるのでしょうか?
0902デフォルトの名無しさんNGNG
> 今まで使ってたS式自体がリストだって事に気づいた

すまん。どうすごいんだ?
0903デフォルトの名無しさんNGNG
すごいよ。マクロのおかげでいろんなことが出来る。
様々なことが出来ることこそが、SchemeがC++やJavaなどより
圧倒的に強力な所以。
0904デフォルトの名無しさんNGNG
>>893
Windowsならコンパイラがほしい。
UNIXだとインタプリタで十分だと思うんだけど
(速さを求めなければそれで良いから、perl,pyhton,rubyのアプリも沢山ある)、
Windowsで何か作って配布でもしようとすると(私がそうするというわけではなく)、
どうしてもコンパイラ言語になる、ということが多いと思う。
0905デフォルトの名無しさんNGNG
>>904
バイトコードっつーか、実行するコードをメモリイメージにしといて、
1つのEXE作るってのはやった事あります。
(コンパイラと名乗れるほど高級じゃなかった。)
そのイメージを適当に圧縮しとけば、まあEXE覗かれたとしても
普通の人はわかんないし。w
そのEXEは、まんまLISPエンジンが載ってるので、
当然ながら外部のLISPコードも読みこめます。

SchemeだとSIODって処理系がたしかEXEつくってくれたんじゃないかと思います。
0906905NGNG
これです
http://people.delphi.com/gjc/winsiod.html
0907904NGNG
>>905
なるほど、エンジンも一緒に乗っけてしまうのか……。
物知らずな私には思いつきませんでしたが
>>906
どうもです。
0908デフォルトの名無しさんNGNG
自分はelispをちょこっといじったことがある程度の情報科の学部2回生ですが、
lispってどのへんが人工知能なのでしょうか?
0909デフォルトの名無しさんNGNG
データとプログラムが完全に分かれていないのは
メリットになるのですが?
0910デフォルトの名無しさんNGNG
>>909
なんかの演算の結果をそのままデーターとして再利用できる。
おんなじことCでやったら、変数宣言して代入して計算してその結果を代入しなおしてその変数を計算して...となる。
0911デフォルトの名無しさんNGNG
>>910
君、なんか違うよ。
0912デフォルトの名無しさんNGNG
>>910
なるほど
0913デフォルトの名無しさんNGNG
>>912
違うってば…
0914デフォルトの名無しさんNGNG
>>908
lisp = 人工知能じゃないです
どのへんも糞もありません

>>910
Cでも変数に代入しないようにプログラムすることは可能です。
つか、「演算結果をデータとして…」って
プログラムコードとデータが分かれてないのと関係ないです。
つか、演算結果がデータでなくてなんなのでしょう?

>>909
マクロとかで便利
0915デフォルトの名無しさんNGNG
>>914
lispて人工知能言語だってよく聞くけど、それはなぜ?
人工知能とどういうふうに関係あるのか聞きたいです。
煽りではなくマジレスで。
0916914NGNG
あ、どのへんが人工知能言語?って話ね。
えーと、なんで人工知能の研究に使われてた(る)んだろうねぇ?
正直、よく知らないです。
記号処理が人工知能研究に向いてるとかでしょうか?

フォローしてくれ > 識者様
0917デフォルトの名無しさんNGNG
人工知能だとか、そういう研究的なことは、普通
のプログラムに比べて極端に難しくて複雑な考え方を
使うわけよ。
だから、言語として一番柔軟性があって記述力のある
Lispが主流ってこと。
0918デフォルトの名無しさんNGNG
>>916
LISPを設計したJ・マッカーシーが人工知能やってたからじゃないの?
一応、マッカーシーは人工知能向けに考えて作ったとの話。
詳細はジョン・マッカーシーで検索
あと、スタンフォード大学にマッカーシーのWebサイトがあったはず。
0919デフォルトの名無しさんNGNG
>>901
LISP系マクロは一回さわっといた方がいいよ。
継続は、制御構造の親玉で、例外処理とかコルーチンなどが
小細工無しで作れたりするんで、結構カルチャーショックがあるかも。
0920デフォルトの名無しさんNGNG
XML関連のシステムってLispで作るのがよさそうね。
0921デフォルトの名無しさんNGNG
http://www.amazon.co.jp/exec/obidos/tg/detail/glance/-/english-books/0262194554
ところでこの本はいったいなんですか?サスマンの本なのですが
0922デフォルトの名無しさんNGNG
まあ自分で自分を拡張してゆくというか
自分で自分のプロうグラムを書き換えてるような所が
昔は人工知能への近道に思えたんでしょうね
0923デフォルトの名無しさんNGNG
>>903
うーん、>>896はまだそこに気づいてないんだな。
S式はsimpleだから便利で強力なんだ。(, ), car, cdr, cons, null, これだけ。

単純な事が力になる、これはよくあることだな。The Internetのbest effort deliverとかさ。
0924デフォルトの名無しさんNGNG
普通はFORTRANでプログラミングしてる時代に生まれたんだから、
数値計算ばりばりでなく、作っては壊しを繰り返し改良を重ねないといけない
人工知能研究に重宝されるのは当然な気がする。
0925デフォルトの名無しさんNGNG
fluid-letって今まで使い道わかんなかったけど、
どうやら既存のコードを変更せずに別の解釈にするって事ができるらしい。

;数値しか引数に取れない+オペレータ
(define (fun a b) (+ a b))
(fun 1 2)
=>3

;これを一時的に他の型に対しても適用させたい。
(fluid-let ((+ generic-add)) ;一時的に+を総称関数化する
 (fun "1" "2"))
=>"3"
0926デフォ@901NGNG
>>923 1ヶ月、Schemeやってて、やっと気付いたのがS式=Listってこと。
いや、マジで、(, ), car, cdr, cons, nullだけで必要十分ですね。
おかげで、思考自体も高度にシンプルになりました。
 「まとめたいものを(と)で束ねる」
それだけ。(これに気付くのに、1ヶ月かかるとは…)
この極度の柔軟性は、逆に当たり前過ぎて、説明しづらい。

しかし、使ってて思ったのが、Schemeは強力か?ってことです。
確かに、知ってるなかで、最高度の思考的柔軟性を与えてくれるが、
シンプル故に、強力さは使用者に依存してしまう。
つまり、想像しうることは(おそらく)すべて表現できるが、
逆に言えば、使用者の想像の限界がSchemeの限界にもなってしまう。

まあ、僕みたいなヒヨッコが使うと強力さを生かしきれないってことです。
0927デフォルトの名無しさんNGNG
>>926
マクロ使うとだいぶ楽になるよ
0928デフォルトの名無しさんNGNG
>>926
SICPがその典型だと思うが、(言語解説部分の短さと内容の豊富さを見よ)
programmingにおいて本題に集中させてくれる、と考えれば嬉しい事だ。

人工知能向きという評価もそういうところから出たと思われ
当時としては極端に複雑なalgorithmを人口知能屋は追求していたわけだから。
0929デフォルトの名無しさんNGNG
>>926
quoteもよろしく.
0930デフォルトの名無しさんNGNG
quasiquoteもよろしく。
0931デフォルトの名無しさん NGNG
>>926
プログラムもデータもすべてS式(リスト構造)であるため,プログラムその
ものが別のプログラムを生成することも,自分自身を書き換えることも出来る
ため,人工知能の研究に向いていました....というか,人工知能の研究のため
に設計された言語です.一方Scheme は,λ計算の過程を学生に見せるために実
装したのが切っ掛けだったと思います.
0932デフォルトの名無しさんNGNG
恐るべき Scheme の威力

(define (A x y)
(cond ((= y 0) 0)
((= x 0) (* 2 y))
((= y 1) 2)
(else (A (- x 1)
(A x (- y 1))))))

(A 1 10)

これを DrScheme でステップ実行したらえらいことになった。
0933Ruby!NGNG
+++++++++++++++++++++++++++++++++++++++++++++++
☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆
Del厨断末鬼の叫び!!!
拙い言いがかりからRubyを必死に煽ろうとしたDel厨が逆襲を受けて死亡!
理論的にDelphiはRubyの足元にも及ばないことが証明された!!!
「Ruby撲滅スレ」
http://piza2.2ch.net/test/read.cgi/tech/1001125342/
★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆★☆
0934デフォルトの名無しさんNGNG
>>932
どうなったの?
0935無名λ式NGNG
>>931
> 一方Scheme は,λ計算の過程を学生に見せるために
> 実装したのが切っ掛けだったと思います.

λ計算ちゃいます。かーるひゅいっとのActor理論です。
(lambda の代わりに(alpha がある、新しいinterpreter作ろうと思ったら、
continuation付きのLisp(=Scheme)があれば十分だった、と。

http://www.cs.umbc.edu/331/resources/papers/Evolution-of-Lisp.pdf読んでみ。
0936デフォルトの名無しさんNGNG
>>935
ごめん... 詳しくはこれ...

ftp://publications.ai.mit.edu/ai-publications/pdf/AIM-349.pdf
0937デフォルトの名無しさんNGNG
板違いだけど、pdfをテキストかhtmlに変換して
英和翻訳してくれるサイトってありませんか?
0938デフォルトの名無しさんNGNG
英語読めないのか...(プ
0939デフォルトの名無しさんNGNG
>>938
ごめんよ(w
英語はまあ、翻訳サイトあるからいいけど、pdfが通らない。
0940デフォルトの名無しさんNGNG
>>938
あ、よかったら要約してちょ(はぁと
0941無名λ式NGNG
ほい>>937
http://www-6.ibm.com/jp/software/internet/king/download.html
0942デフォルトの名無しさんNGNG
>>941
すいません。
うちの環境がクソすぎて、ソフトはもういれらんないのです。
これ以上はスレの迷惑になるので諦らめます。
他の方法を模索します。(パソコン買い替えるなど)
ご迷惑お掛けしました。
0943デフォルトの名無しさんNGNG
以前 bitに Sussmanさんだかに Schemeの生い立ちのインタビュー記事が
ありました。2ヶ月にわたって載ってた。
何年何月号だったかわ今はわかりませんけど、そこに >>935 さんの言って
たような事が書いてありましたよ。
デッカクなる前の bit だったと思います。
0944943NGNG
Scheme過去・現在・未来(前編) bit 1996/04
Scheme過去・現在・未来(後編) bit 1996/05

Guy L. Steele Jr. (訳 井田昌之)

でした。
0945デフォルトの名無しさんNGNG
>944
図書館に行けば見れるかな?
いいかげんpdfでもなんでもいいから電子化してほしい・・>蔵書
0946デフォ@901NGNG
継続を学ぶためのお勧めの情報源にはどんなものがありますか?
0947デフォルトの名無しさんNGNG
>>945
> 図書館に行けば見れるかな?

bitは世田谷区図書館レベルでもあったな。
0948デフォルトの名無しさんNGNG
(((lambda(r)(set! r(lambda()(r))))'米国が攻撃開始))
0949おいおいNGNG
(set! r (lambda () (r))) の帰り値は未定義だぞ
0950 NGNG
(define terrorism (lambda (x y) (reprisal y x)))
(define reprisal (lambda (x y) (terrorism y x)))
0951デフォルトの名無しさんNGNG
(cons 1 (cons 2 (cons 3 '())))と
(list 1 2 3)
てどっちが速いの?
0952デフォルトの名無しさんNGNG
>>951
作りによるだろ
終端がnilで良いならlist使っとけ
0953 NGNG
`(,x ,y ,z) と
(list x y z)
てどっちが速いの?
0954デフォルトの名無しさんNGNG
>>953
quasiquoteの実装具合によるだろ
おれっちの環境ではlistが圧倒的に速いけどさ
0955デフォルトの名無しさんNGNG
(list* a b c)
と
`(,a ,b ,@c)
てどっちが速いの?
0956デフォルトの名無しさんNGNG
guileを使っていろいろと遊んでいるところなんですが、
これを終了させるのになにかいい方法はないですか?
いまはCtrl+zしてからkill -9してるんですが、皆さんどうされてますか?
0957デフォルトの名無しさんNGNG
>>955
list*
qquoteは余計な解析パスが掛かる。
>>956
(exit)とか(quit)って無かったっけ。
0958デフォルトの名無しさんNGNG
>>957
!!!ありがとうございます!!!
これを知らずに何日苦労したことか・・・
0959デフォルトの名無しさんNGNG
>>958
Ctrl-D(=端末からのEOF)でもOK。
0960デフォルトの名無しさんNGNG
そろそろ次スレ立てて欲しいところなんだけど、
その前にリンクの整理と参考書籍をまとめようよ!
0961デフォルトの名無しさんNGNG
>>960
とりあえず次スレ立てておきました。
リンク先とかは2以降ということで。
LISP Scheme Part2
http://piza2.2ch.net/test/read.cgi/tech/1002584344/
0962デフォルトの名無しさんNGNG
Schemeについて日本のポータルサイト(?)
http://www.sci.toyama-u.ac.jp/~iwao/Scheme/
0963デフォルトの名無しさんNGNG
■■■■ 推薦書籍 ■■■■

【計算機プログラムの構造と解釈(SICP)】
日本語 http://www.amazon.co.jp/exec/obidos/ASIN/489471163X
原書 http://www.amazon.co.jp/exec/obidos/tg/detail/glance/-/english-books/0262011530

私はこれだけしか読んでないヘタレなので、あとは識者の方、下のリンクから推薦書籍をあげて下さい。
よろしくお願いします。
個人的にはいつの間にか刷られていた、CommonLisp 2edが欲しいところです。
http://www.amazon.co.jp/exec/obidos/tg/detail/glance/-/english-books/1555580416


アマゾン "Scheme" 和書検索結果
http://www.amazon.co.jp/exec/obidos/search-handle-form/250-7032484-4473008

アマゾン "Scheme" 洋書検索結果
http://www.amazon.co.jp/exec/obidos/search-handle-form/250-7032484-4473008

アマゾン "Lisp" 和書検索結果
http://www.amazon.co.jp/exec/obidos/search-handle-form/250-7032484-4473008

アマゾン "Lisp" 洋書検索結果
http://www.amazon.co.jp/exec/obidos/search-handle-form/250-7032484-4473008
0964デフォルトの名無しさんNGNG
SICPへのリンクは?

http://mitpress.mit.edu/sicp/full-text/book/book-Z-H-4.html#%25_toc_start
0965デフォルトの名無しさんNGNG
すいません、検索結果へ直接は飛べないみたいです。
ごめんなさい。
0966デフォルトの名無しさんNGNG
>>963
Web で読めるよ
0967デフォルトの名無しさんNGNG
>>966
http://mitpress.mit.edu/sicp/full-text/book/book-Z-H-4.html#%_toc_start
0968964NGNG
>>967

俺の書いたのと何が違うんだ?まあいいけど。
0969Part2の1NGNG
2へ適当にリンク貼っておきました。
足りない様でしたら補完おねがいします。
0970デフォルトのん足NGNG
>>969
ありがとうございます
0971 NGNG
がいしゅつ?

"The Scheme Programming Language Second Edition"
http://www.scheme.com/tspl2d/index.html

日本語訳では「プログラミング言語Scheme」という本になってるよ。
0972デフォルトの名無しさん NGNG
>>971
初出みたいですね。でも関数言語の本ってWebに公開されて
いるものが多いですね。教科書として毎年生徒の数だけ
売れることが約束されているからあんまりセコくならないのかな?
英語だと世界中で教科書として使われるわけだし。
0973デフォルトの名無しさんNGNG
Common Lisp the Language, 2nd Edition
http://www.math.uio.no/cltl/clm/clm.html
0974デフォルトの名無しさんNGNG
C言語 a = b = c;
Scheme (set! a (begin (set! b c) b))
うむむ・・
0975デフォルトの名無しさんNGNG
>>974
副作用が基本の言語と比べるのって...
0976デフォルトの名無しさんNGNG
>>974
記述量を問題にしてるならマクロつかえ
0977デフォルトの名無しさんNGNG
(define b a )
(define c a)
ぢゃだめなの?
0978 NGNG
{hoge ... } => (begin hoge ...)
みたいなマクロって書ける?
0979デフォルトの名無しさんNGNG
>>978
まずカッコが無いとだめ。
(operator args)
が基本なので、無理矢理やるとしたら
({ hoge... ) => (begin hoge ...)
0980デフォルトの名無しさんNGNG
>>980
マクロ文字というのがある。
Schemeでは規定されてないけど、
厳密なLISP処理系ではマクロ文字が定義できる筈。
`',,@(←こういうのは本来マクロ文字。)
マクロ文字は演算子に近いので、シンボルなどと
くっつけて書いても区別される。
'a => (quote a)
マクロ文字は無いけど、どうしても使いたい場合、
(read)を修正するとか。
0981デフォルトの名無しさんNGNG
>>978
0982デフォルトの名無しさんNGNG
>>981
はげしくどうい!
0983デフォルトの名無しさんNGNG
プログラマー板「リスプ」より
http://mentai.2ch.net/test/read.cgi/prog/963134110/

> franz Lispにあるfexprって言う関数は
> XLispにありません。
> exprから誘導出来ますか?

FEXPRは、可変個引数でかつ引数を評価しない関数なので、
マクロで書き直しましょう。引数が評価されてもいいなら、

(defun fname (&rest arg) ふにゃふにゃ)

で可変個引数にしてもいいです。
0984Lisp板の753NGNG
>>983さん
Thanx
今問題のソースPLT Schemeに移植してますがてんとう虫が出まくってます。
あと もし関数に渡す引数が評価されては、まずい場合はどうなんでしょうか?
0985デフォルトの名無しさんNGNG
>>984
だから、マクロで全部解決するって・・
0986Lisp板の753NGNG
(define-macro prove fexpr (wff)
(wang (addr (car wff) (line 0 nil nil nil nil)))
こんな感じでしょうか?
0987デフォルトの名無しさんNGNG
)
define-macro: malformed definition
>
ちゃんちゃん
>malformed definition
    ↑
これもう見飽きました
Xlisp-statに帰ります。
0988デフォルトの名無しさんNGNG
>>986
> (define-macro prove fexpr (wff)
> (wang (addr (car wff) (line 0 nil nil nil nil)))
> こんな感じでしょうか?

XLispってschemeじゃないよね。

< (defmacro prove (wff)
< `(wang (addr (car ,wff) (line 0 nil nil nil nil)))

じゃねーの? XLispにbackquoteあるかどうか知らんけど。
0989デフォルトの名無しさんNGNG
Schemeでnilを定義するばあい、
(define nil '())
(define nil #f)
どっちがいいんでそ?
0990デフォルトの名無しさんNGNG
Lispスレの765さん
>(define-macro fexpr (lambda rest body...))
これはマクロでfexprを定義しているって事ですよね?
カキコしながら またダメ
> (define-macro fexpr (lambda rest body))
> (define prove fexpr (wff)
(wang (addr (car wff) (line 0 nil nil nil nil)))
)
define: malformed definition
>         ↑
       ちゃんちゃん
0991デフォルトの名無しさんNGNG
>>988
ありがとうございます
0992Ruby戦隊NGNG
Ruby >>>>>>>>> Scheme
0993Ruby戦隊NGNG
             
Ruby >>>>>>>> Scheme
0994ruby!NGNG
Ruby!!!!!!!!
0995Ruby!NGNG
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
0996ああああああああNGNG
                         
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
0997Ruby戦隊NGNG
                        
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
0998__ruby!__NGNG
_______________                       
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
0999__RUBY__NGNG
^^^^^^^^^^^^_______________                      
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
るびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびーるびー
10001000!NGNG
Ruby >>>>>>> Scheme
10011001Over 1000Thread
このスレッドは1000を超えました。
もう書けないので、新しいスレッドを立ててくださいです。。。
レス数が1000を超えています。これ以上書き込みはできません。