SBCL 1.0 Released! 57
ストーリー by kazekiri
括弧の逆襲 部門より
括弧の逆襲 部門より
Anonymous Coward 曰く、
Steel Bank Common Lisp 1.0がリリースされました。 SBCLはCMU CLから分離したCommon Lisp処理系で、より多くのプラットフォームをサポート、ネイティブスレッドのサポート、Unicodeと主要なロケール(EUC-JP、Shift_JIS含む)をサポートなどの特徴があります。
Lispと言えば遅いという印象があるかもしれませんが、Computer Language Shootoutの結果ではトータルでJavaよりもパフォーマンスが高くなるなど、かなり高性能な処理系です。
Lispと言えば遅い (スコア:2, すばらしい洞察)
いや、第一印象は「Lispと言えば括弧が多い」が多数派だと思うに100ガバス。
# 論点が違うのは百も承知なのでAC
Re:Lispと言えば遅い (スコア:1, おもしろおかしい)
# 無粋なのでAC
Re:Lispと言えば遅い (スコア:1)
えーと (スコア:1, おもしろおかしい)
笑うところですか?
Re:えーと (スコア:0)
じゃ大して速くないじゃんと小一時間(以下略)
# 男は黙ってC++なのでAC
Re:えーと (スコア:0)
Re:えーと (スコア:1, おもしろおかしい)
Re:えーと (スコア:0)
個人的にEmacsよりコンパクトで好きです。
xyzzy Lisp Programming
http://www.geocities.jp/m_hiroi/xyzzy_lisp.html
Re:えーと (スコア:0)
Re:えーと (スコア:0)
Re:えーと (スコア:0)
笑いどころはこっちだろ。
よくある「elispのアプリは遅い。Cで書き直せ」みたいな話を
「Lispは遅い」と前提もなにもなく鵜呑みにした、その上で
スクリプト言語の紹介でPerlでもPythonでもよく使われる
「**な処理でベンチマークを取ったらJavaより速かった」的な記述をこれまた
自家バイアスかまして解釈したんだと思われ。
これまでのインタプリタ型言語の比較で、Lisp系のものが全般に
他より遅いという話は聞かない。逆ならよく聞く。
Javaな人が「この処理ではCより速かった」とか言って喜ぶように
スクリプト言語の愛好者は「Javaより速かった」と宣伝する。
そういう当り前の光景も、見る人が見ればここまで勘違いできる、好例だな。
Re:えーと (スコア:0)
推測でよくそこまでわかりましたね。エスパーですか?
Re:えーと (スコア:0)
Re:えーと (スコア:0)
Lispと言えば遅いという印象...? (スコア:1, 参考になる)
Lisp プログラマのための Python 人門
http://www.unixuser.org/~euske/doc/python/python-lisp-j.html
そんなにバカにされるほど遅いのかな?
Re:Lispと言えば遅いという印象...? (スコア:0)
参考にならなくはないけど、2002年のデータじゃ、現実と乖離している感が否めない。
Re:Lispと言えば遅いという印象...? (スコア:0)
(C++を1としたもの)
例外処理 0.01
リスト処理 0.93
単語を数える 0.73
例外処理はすげぇと思うが、残りの2つずるくない?
リスト処理や単語を数える時のパースの速度は事前処理って事じゃないの?
ファイル中の数値を総計 7.54
だよ?
Nerds御用達言語 (スコア:1)
comp.lang.lisp > How I lost my faith (very long) [google.com]を読むとLispってのは
Nerds御用達言語らしいというのが想像できて、あこがれます。2つの記事を(超)要約すると
「Lispを使えば短期間で開発ができて、コードの量も非常に小さくできる。PythonはLispの再発明だ」
ということです。しかし、ヘタレなぼくにはそのすごさがいまいち理解できません。そこに書かれている
(defun foo (n)
#'(lambda (i) (incf n i)))
はいったい何をしたいのでしょうか。Lisperの方、教えてください。
Rubyとの関連についてはRe: Paul Graham essay on language popularity /// Ruby Lambda [nagaokaut.ac.jp]
に書かれています。
あと、Lispは方言が多すぎるということに近づきがたい印象を持ちます。今回またSBCLという
Common Lispの1方言ができたのでしょうか。
love && peace && free_software
t-nissie
Re:Nerds御用達言語 (スコア:1)
Lispに方言が多かったのは、過去の話じゃないですか。いまはANSI Common Lisp標準がありますから。もちろん処理系によって細かい差異はあるんですけど、それはC言語なんかでも同じですよね?
標準 (スコア:1)
WHY Common Lisp? [msi.co.jp]を読むとそうみたいですね。
で、SchemeにはR5RSがあると。
> In 技術野郎の復讐---Revenge of the Nerds---
> * これが、他のLisp方言におけるアキュムレータジェネレータのコードだ。
> Scheme: (define (foo n) (lambda (i) (set! n (+ n i)) n))
> Goo: (df foo (n) (op incf n _)))
> Arc: (def foo (n) [++ n _])
Emacs は (defun foo (n) '(lambda (i) (incf n i))) でしょうか。
各Lispの方言の中では標準が固まっているといってよいのでしょうか。
しかし、各方言の特徴をWikipediaなんかで読んでも話が高度すぎて
畏れ多いというか、わけがわからないというか…
love && peace && free_software
t-nissie
Re:標準 (スコア:3, 興味深い)
念のため突っ込みを入れておくと、Emacs Lispにはclosureが無いので、これは意図通りに動きません。 例えば、元コメントの関数fooを定義した後で、以下を実行してみるとCommon Lispとの違いが分かります。
Common Lispでは2, 3, 42が順に表示されますが(1.0じゃないけどSBCL 0.9.16で確認)、 Emacs Lispでは43, 44, 44が順に表示されます(Emacs 21.3で確認)。fooの返す関数に使われている変数nが、Emacs Lispでは関数を呼び出した箇所の変数nを指している一方、 Common Lispでは元のfooの定義に現われる変数nを指している(そしてfooの呼出時に新たに作られた束縛を参照している)ことになります。 このことを、Emacs Lispは変数がdynamic scopeを持ち、Common Lispでは(defaultでは)lexical scopeを持つと言ったりします。
しかもCommon Lispの変数は(defaultでは)無限のextentを持つので、fooの呼び出しで作られた束縛が、 その後の「(Paul Grahamの言う)アキュムレータ」呼び出しでも参照され、次々と更新されていく様子が分かるかと思います。 Emacs Lispでも(値が違うものの)一見数値がインクリメントされていますが、 更新されているのは、アキュムレータを呼び出している側のlet式の変数nです。Common Lispではlet式の変数nは更新されていません。
t-nissieさんのコメント中の定義で使われているincfはEmacs Lispでは cl.el("Common Lisp extensions for Emacs")に含まれるマクロです。 「Common Lisp拡張」という名前ではありますが、 incfのようなちょっとしたマクロをそれっぽく定義することはできても、 変数のscopeやclosureまでCommon Lisp互換にするのはさすがに実現できていません。 というわけで、Paul Grahamの言う「言語の相対的な力」というのがclosureの書きやすさで決まるのなら、 Emacs LispはCommon Lispと違い、論外の超弱々言語ということになるかもしれません。:-) まあclosureは確かに便利というか、(プログラムで高階関数を使いだすと)むしろ「無いとストレスが溜る」ものなので、 Paul Graham氏の主張も分からないではないですが。
なお、「イマドキclosureを説明するのにmutableな変数を前提とするってのはどうよ」などの突っ込みは、 Paul Grahamさんに直接おっしゃってください。 Paul Grahamの定義ではHaskellとかは相対的に弱い言語ってことになったりして? :-p
Re:標準 (スコア:2, 参考になる)
う、調べず書くもんじゃない……。
というのは嘘でした。Common Lisp extensions for Emacsを使うと、元コメントのアキュムレータは以下の様に定義できます。
Common Lisp Extensionsに含まれるlexical-letを使うというのがミソですね。 このfooを元コメントのように使ってやると、ちゃんと2, 3, 42を順に表示します。 というわけで、Emacs LispもPaul Graham氏に見放されずには済みそうです。ごめんなさい。
まとめ (スコア:2, 興味深い)
まだclosureとか本質はわかっていませんが、とりあえず各言語で試してみました。
● Common Lisp (CLISP。sbcl-1.0 は、Linux kernel の NPTL threading を使う
らしく、今使っているちょっと古めのLinux Boxにはインストールできませんでした。)
$ clisp
[1]> (defun foo (n) #'(lambda (i) (incf n i)))
FOO
[2]> (defvar bar (foo 5))
BAR
[3]> (funcall bar 3)
8
[4]> (funcall bar 7)
15
[5]> (exit)
● Scheme (Gauche)
$ gosh
gosh> (define (foo n) (lambda (i) (set! n (+ n i)) n))
foo
gosh> (define bar (foo 5))
bar
gosh> (bar 3) ; なぜfuncall等が不要なのか?
8
gosh> (bar 7)
15
gosh> (exit)
; Gaucheはreadlineがないので入力時に発狂しそうになりました。
; 通はEmacsから使うそうですが。
● Emacs Lisp (in *scratch* buffer, with C-j)
(version)
"GNU Emacs 22.0.91.1 (i686-pc-linux-gnu, X toolkit, Xaw3d scroll bars) ..."
;; Common Lisp extensions for Emacs
(require 'cl)
=> cl
(defun foo (n)
(lexical-let ((n n))
(function (lambda (i) (incf n i)))))
=> foo
(defvar bar (foo 5))
=> bar
(funcall bar 3)
=> 8
(funcall bar 7)
=> 15
● Ruby
$ irb
irb(main):001:0> def foo(n)
irb(main):002:1> lambda {|i| n += i}
irb(main):003:1> end
=> nil
irb(main):004:0> bar = foo(5)
=> #<Proc:0x40222a3c@(irb):2>
irb(main):005:0> bar.call(3)
=> 8
irb(main):006:0> bar.call(7)
=> 15
irb(main):007:0> qux = foo(1)
=> #<Proc:0x40222a3c@(irb):2>
irb(main):008:0> qux.call(2)
=> 3
irb(main):009:0> qux.call(3)
=> 6
irb(main):010:0> bar.call(1)
=> 16 (barとquxとは独立。しかし、p bar と p qux とが同じなのが謎。)
irb(main):011:0> exit
love && peace && free_software
t-nissie
Re:まとめ (スコア:1)
あ、日記 [srad.jp]でですね。 すみません、気付いてなかったので「余計なもの」になってました。(_ _)
これは、Schemeでは名前の関数値と変数値に区別がなく、 リスト先頭の要素も他の要素と同様に評価される(R5RSの"4.1.3. Procedure calls"のところ)からです。 なので、Schemeでは なんてのも書けます(R5RSより引用)。一方Common LispやEmacs Lispでは、変数値と関数値は別々に扱われます。 Common LispやEmacs Lispで、
とかやると分かると思います。 同じ名前でも関数と変数が区別される処理系では、 とか書けますが、これは逆にSchemeでは動きません。Re:標準 (スコア:1)
GooやArcは、Common Lispより後に生まれた新しいLisp方言で、正直、Common Lispに飽き足らない人向けですから、これからLispを始めようという人はCommon LispかSchemeのどちらかに手をつけるといいと思います。Common LispもSchemeも多数の処理系がありますが、どちらも標準がありますよ。
Re:標準 (スコア:0)
どうも標準化ってのが、単にいろいろ不便にしてるだけとし
か思えないまま過ぎ去った10ウン年
(defun ac (x y)
(cond ((zerop x) (+ y 1))
((zerop y) (ac (- x 1) 1))
(t (ac (- x 1) (ac x (- y 1))))]
とか
(defun factorial (n)
(cond ((zerop n) 1)
直ってるのかなぁ? (スコア:1, 参考になる)
関連ストーリー (スコア:0)
ってあーた、五月のトピで1コメントって何よ、ものすごく関心薄い?
興味本位で聞きますがLISPで大規模(人数的にの意味ね)開発する事とかあるのでしょうか?
言語環境とか言語の生まれのせいか、一人か二人でコツコツフィードバックループで作る様な気がするんですが。
#個人的にはemacs-lisp以外あまりさわったことないんでAC
Re:関連ストーリー (スコア:3, すばらしい洞察)
ソフトウェア的なパーツがあらかじめ想定できるような簡単な問題なら,Lispを使うまでもないかも.
一人で開発しているだけなら,リスト構造のその場限りで構造決めて,どんどん先へ行けるという良さがあるのですが,人間が増えるとそうもいかなくなってくるのはどんな言語でも同じ.関数やマクロのすりあわせとか,いいかげん?なリストの使い方ができなくなってくると大して変わらないか..
#多人数開発はしたことないけど,いろんな意味で開発の効率は数段は違うような気がしますけどね.
Re:関連ストーリー (スコア:0)
多人数でソフト書くときってクラス指向の言語だとオブジェクトのインターフェースのすりあわせとかその資料化とかに一番時間使うじゃないですか。(最初にきっちり決めておいてプログラマの責任境界面をちっちゃくするかわりに大人数で分割処理的な)
LISPにおけるその界面って何なのだろうって言う疑問なわけです。
で2,3の書き込みを見てオモッタのは、やっぱり大人数でなく人数的に小規模ですまして
書き換えサイクルの短い開発を高速で回す感じなのだなぁと言うところでしょうか?
Re:関連ストーリー (スコア:2, 興味深い)
せいぜい10人まで。2〜3人が一番多いかな。
オブジェクトのインタフェースがプロジェクトの最初の方で決められるような
仕事なら、Lispを使う必要も無いと思います。
だいたい、最初は何がどうなるのかよくわからん状態なのを手探りしつつ
時には力業でわっと一度動かしてみる、ってな感じの話が多いです。
オブジェクトのインタフェースが決まったら、実装も出来ちゃってるって
パターン。そういう仕事だと人数増やしても効率あがらないですしね。
Re:関連ストーリー (スコア:2, 参考になる)
どういったことを心配しておられるのか良く分からないのですが、Common Lispは言語仕様に関してだけ言えば、 多人数で問題が起こる理由は特に無いように思います。
まず、大きなプログラムを分割して複数のグループで作っていくということであれば、 Common Lispにおいて典型的には、packageで分割することが考えられます。 packageというのは名前空間を分割する仕組みです。 PythonやRubyにも似た機能があると思いますが、 外部に対してexportする名前と内部でだけ使うinternalな名前を区別したりできます。 package名とexportする名前のところで、しっかりインタフェースを擦り合わせておけば、 各package内は他の部分に影響されずに実装できます。理屈の上では。
muさんのコメント [srad.jp]を見ると、 Lispではなんでもかんでもリスト構造で表現するという印象があるように読めなくもないのですが、 実際にはCommon Lispでも構造体を作ることができ、内部表現が変わってもそれに対するインタフェースは変えないでおく、 といったことも一応できます。構造体参照はアクセサ関数経由になりますので、アクセサ関数の形さえ変えなければ、後からどうとでもなるということです。ですので、 「その場限りで構造決めて,どんどん先へ行」ってしまっても、後でプログラムの他の部分を変更することなく、 構造だけ考え直すとかいうことはできます。最初に決めたインタフェース自体が駄目だった場合苦労するのは他の言語同様ですが。
「クラス指向」でないと駄目ということでしたら、 Common Lisp仕様にはCLOS [wikipedia.org]というオブジェクト指向システムが含まれています。 これはANSI仕様にも入っていますので、ANSI Common Lisp準拠の処理系(SBCLとか)なら使えるはずです。 C++やJavaとはちょっと毛色は違いますが、クラスベース(ECMAScriptなどのようなプロトタイプベースでなく)オブジェクトシステムになっています。
というような開発方法をとりたければ、CLOSベースでインタフェースを決めるのも手かもしれません。 実際にはpackageも一緒に考えることになると思いますが。……というように、言語仕様上は多人数開発もOKかと思うのです。 しかし、大きなプロジェクトをCommon Lispで立ち上げるのが難しいとしたら、 それはやはりmuさんも指摘しておられるように、Lispを使える開発者が集まらないという点に問題があるんだと思います……。orz
;; 最近そこそこ多人数なC++でのプロジェクト内で「ああっ、ここLisp(もしくはScheme等々)ならもっと楽に書けるのにっっ」とか
;; (心の中で)叫ぶ日々を送ってます。(T_T)
Re:関連ストーリー (スコア:1, 参考になる)
こちら [msi.co.jp]のリンクはってみますね。
Re:関連ストーリー (スコア:0)
(1) 納豆相手にくさやを出して、納豆の方が臭い
(2) 納豆相手にくさやを出して、くさやの方が臭い
(3) 納豆相手にくさやを出して、どちらも臭い
(4) 納豆相手にくさやを出して、どちらも芳しい
Re:関連ストーリー (スコア:2, 参考になる)
大規模って程大規模ではなかった(二十人は越えなかったかな?)ですけど、 数年間、 主に Common Lisp で開発してた研究プロジェクトに派遣されてたことがありますよ。 AI・自然言語処理がらみでした。
処理の速さよりも、 特定分野での書き易さ(開発の速さにつながる)でしょうかね、 Lisp の利点は。 『手続き』ではないものを、 わざわざ『手続き』に翻訳しなくてもいいので。
;; Native Lisper ではないので、
;; あんまり偉そうなことは言えないけど。
Re:関連ストーリー (スコア:2)
> ってあーた、五月のトピで1コメントって何よ、ものすごく関心薄い?
日付は2001.5.10ですよ.
そして,このスラッシュドットジャパンが始まったのは2001.5.28
http://srad.jp/about.shtml [srad.jp]
Re:関連ストーリー (スコア:0)
プロジェクトへの導入 (スコア:1)
1)Lisp インタプリタ作る
2)簡易言語的な wrapper 作る
3)目的に応じた要素篇を人海戦術で作らせる
とかね。
Re:関連ストーリー (スコア:0)
# 大規模とは言えないですけどね、、、
Re:関連ストーリー (スコア:0)
computer algebra system(数式処理)のMAXIMAが思い浮かびます。
数学とLispの両方に通じていないといじれない為、大規模とはいえませんが。
amd64なマシンでは、clisp,sbcl等が使えるので、 暇を作って新しいsbclを試してみようとは思います。
へー (スコア:0)
ちょっくら使ってみようかな。
SBCL・・・ (スコア:0)
λの時代来たる!! (スコア:0)
Re:λの時代来たる!! (スコア:1)
Lambda Camel Perl 6って何なのか知らないのですが、Perl 6では従来のclosureの他に、blockがすべてclosureと見做されるようになって、新しい記法が追加されるという 話 [perl.org]の関連でしょうか?
λの時代なのかどうかは正直よく分かりませんが、 Javaにクロージャ [srad.jp]のストーリーでも 紹介 [srad.jp]されているように、 C++にもlambda式を入れる提案があるようで。もしかすると流行ってるのかなあという気もちょっとしますね。LISPは通り越してML系の言語を目指してる気もしますが。
オブジェクト指向が流行った(?)おかげで、今やCOBOLの仕様すらオブジェクト指向を取り込んでるそうですが、 関数型言語が本当に流行ったら、そのうちFUNCTIONAL COBOLなんてのも登場するんでしょうか。:-)
Re:λの時代来たる!! (スコア:2, 興味深い)
;; 「実はRubyやPython等は見栄えを変えたLispなので、LispはRubyやPythonのいる正にその位置に(も)いる」
;; という主張をする人 [srad.jp]もいるかも? (#1068899さんネタに使ってごめんなさい)
「RubyやPythonの位置」って何だろうと考えていて、 ここ/.Jとかでも時々見掛ける展開、「RubyやPythonはトイプログラムにしか使われていない」なんて煽りに対し、 「いやいや実は○○はRuby(またはPython)を使ってる」と返答が帰ってくる、 お決まりのパターンを連想しました。 これになぞらえて想定問答をやってみると、こんな感じになりましょうか。
「LISPなんて使われてない」→「いやいや、EmacsがEmacs Lispで書かれているのは言うに及ばず、 画像処理の定番GIMPのScript-fu [gimp.org]はSchemeだし、 かつてGNOMEの標準Window Managerだったsawfish [sourceforge.net]が使っているrepもLISPだし、Maxima [sourceforge.net]とか……」
「商用ソフトでは使われてない」→「えーと、AutoCADはAutoLISP [wikipedia.org]でカスタマイズできるらしいですよ。」
「実用的なシステム、大規模システムとか高信頼システムには使えない」→「Paul GrahamはよくViawebを立ち上げた話 [practical-scheme.net]を引き合いに出してLISPの有用性を語ってますね。 米国防省の航空気象情報システムはSchemeでXMLデータ処理 [okmij.org]をしているらしいし、 Yahoo! Picks [yahoo.com]てサイトも Schemeを使って [utah.edu]構築したそうですよ。 そういえば、NASAの火星探査でもCommon Lispが大活躍 [franz.com]って知ってました? 他にも色々 [franz.com]と……」
ジョークのネタにもなるLISPの括弧ですが、 その括弧もまた、LISPに比類無き力を与えているものの一つなんだ、 という考え方もあります。 例によってPaul Graham氏も 熱く語って [dreamhost.com](「マクロ」について語っている辺り)おります。^^;そんなわけでCommon LispやSchemeが今もS式を直接使っている一方で、 プログラムを生のS式で書かないように「頑張っているもの」も過去から現在まで、 これまた実はたくさんあります。
そもそも1960年のJohn McCarthyの歴史的な論文 Recursive Functions of Symbolic Expressions and Their Computation by Machine, Part I [stanford.edu] の中からして、処理対象のS式と区別するために、 M式という(幾分他の言語の関数表記と似ているかもしれない)記法が登場しています (元ACさんの意図とはちょっと目的が違うかもしれませんが)。
LISPを、S式表記でなく、他の言語のような「普通の」表記で書く試みは、 その後も繰り返し登場します。 例えば数式処理システムREDUCE [wikipedia.org]は、 Algol風文法を持つRLISPで書かれているとあります。
もっと有名(?)な例としては、1967年に作られ、 1980年代ごろ日本でも児童教育用あるいはそのタートルグラフィックスで話題になった LOGO [mit.edu] は、括弧を(あまり)使わず書けるように工夫されたLISP方言の一種だったと言えます。
最近の例としては、 Dylan [opendylan.org]が最初はS式を使っていたのを、 その後Algol形式の文法に変えています。 どんな感じかはWikipediaの Dylan [wikipedia.org]の項目が比べやすいと思います。 DylanはAlgol風表記なのにマクロ [opendylan.org]を持っているという辺り、かなり「頑張っている」かもしれません。 ……と言いつつ私自身は勉強不足でDylanを分かっていないので、 ボロが出ないようこの辺で退散します。(_ _)
余談になりますが、 Lisp以外でも関数型言語を使っていると、 ちょっと油断するとLispみたいに括弧だらけの プログラムになっていることがよくあります。 関数Aを適用した結果にBを適用し、その結果にCを適用して……なんてことが 多いからですが、 そんな時「じゃあ最初からS式で書いとけばいいじゃんっ」とか思ったりもします。 しかしその一方で、Haskellの$オペレータを知った時、 簡単な仕掛けなのに、括弧を減らして見やすくする(ような気がする)工夫として、 ちょっと面白いなあと思ったりもしました。 私自身の中でも、S式の方が見やすいのかそうでないのか、 実はまだアンビバレンツな感じなのかもしれません……。 レベル6 [practical-scheme.net]はまだ遠い(それよりずっと下も)……。^^;
Re:λの時代来たる!! (スコア:1)
Perl/Python/PHP/Rubyでevalを使うことになったとき、Lispのカッコの偉大さに気付く。少なくとも僕はそうだった。
LISPの普及を阻害する (スコア:0)
Re:LISPの普及を阻害する (スコア:2)
CommonLispとScheme
に収斂してきているような気がしますが.
あとEmacsのelispぐらいでしょうか.
#まあ,普及してないのは当たってますがorz
Re:LISPの普及を阻害する (スコア:0)
処理系となると標準てありますか?
まさか全ての処理系がまったく同じ挙動という訳ではないでしょう?
Re:LISPの普及を阻害する (スコア:1, 興味深い)
その見方は新しいかも。
例えばCなら標準に対して様々な処理系があってそれぞれに使われています。一方でPerlやJavaのように比較的新しい言語はまず実装ありきで、標準規格のないものも少なくないです。
# 最近の言語でもECMAScriptやC#は例外か
LISPやSchemeは割と古い言語で標準規格もある。実装もいくつかある。そういう意味でCに近い気がします。
>まさか全ての処理系がまったく同じ挙動という訳ではないでしょう?
たしかにそうですが標準規格と異なる挙動はバグです。LISPに限らずバグによる誤った挙動を期待することは、いつ梯子を外されるかわからないため危険です。様々な制約によりworkaroundする時もあるけれど、それもLISPに限らないですよね。