Archive for 10月, 2008
Cyan
火曜日, 10月 28th, 2008若干流行に乗り遅れた感じはありますが、
Cyanを触ってみました。
色々気になったけど、時間が無いから一点だけ。
関数の中で関数を作れるのか試してみたんですが、
def(reverse)^(lst): iter:=^(lst2, acc): say(lst2) if (lst2.null?()): acc else: iter(lst2.cdr(), [lst2.car()|acc]) iter(lst, []) reverse([1,2,3,4,5]) # => [5, 4, 3, 2, 1] # 出力されるのは # [1, 2, 3, 4, 5] # [2, 3, 4, 5] # [3, 4, 5] # [4, 5] # [5] # []
これは上手く動きますが、
次のコードだと、
def(reverse)^(lst): iter:=^(lst, acc): say(lst) if (lst.null?()): acc else: iter(lst.cdr(), [lst.car()|acc]) iter(lst, []) reverse([1,2,3,4,5]) # => (無限ループで結果出ず) # 出力されるのは # [1, 2, 3, 4, 5] # [2, 3, 4, 5] # [2, 3, 4, 5] # [2, 3, 4, 5] # [2, 3, 4, 5] # ...(以下同様)...
何故か無限ループに陥ってしまいます。
iterに代入される関数の参照してる「lst」が外側のlstかとも思ったんですが、
一度だけはCDRが取れてるし、そういう仕様でもなさそう。
試しにこんなコードを動かしてみたんですが、
m=100 def(f1)^(): i:=^(n): say(n+m) i(1) m:=3 i(1) m:=2 i(1) f1() # 出力されるのは # 101 # 4 # 3
このように動くのを見たところ、関数内部における変数への参照があると、
定義された環境から外の環境に向かって、順番に変数を探すように思えるんですが、
引数の場合だけ何か扱いが違うんですかね。
ローカル変数の取り扱いの説明が、この記事だけだと、分からないところが多いので、
出来れば詳しい説明をお願いします。
毎月20日はノーマイカーデー
火曜日, 10月 21st, 2008ニコニコ動画にShibuya.lisp Tech Talk #1の開会の挨拶があがってました。
Shibuya.lispテクニカル・トーク#1 開会の挨拶 ひげぽん
(要アカウント)
最初のスライドに”Why Lisp?”と書いてありますが、
この言葉、何処かで聞いたことがあるな…と思って調べてみたら、
「OnLisp」の1.5節が”なぜ(またはいつ)Lispか”というタイトルで、
今や問いはなぜLispか?ではなくいつLispか?になっている.
なんて書いてました。
残念ながら少なくても日本ではいまだに「なぜLispか?」の時代みたいです。
前々から言っていた、SHIORIの問題ですが、ぽなさんに解決法を教えていただきました。
仕様の見落としという非常に恥ずかしい原因でした…なんとも恥ずかしい。
そんなわけで、ようやく前に進めました。
しかし、うかべんまで本当に時間がなくなってきた。
非常にまずい感じです。
17日のリリカルの続き
続・OnTranslate(以下略)
金曜日, 10月 17th, 2008とりあえず、OnTranslateメッセージがやってきたときに、
直前に送ったリクエスト再び送るようにしてみました。
SHIORI/3.0 200 OK Sender: matsuri Charset: UTF-8 Value: \0\s[0]\1\s[10]\0おはー\1らっきー\e
GET SHIORI/3.0 ID: OnTranslate Sender: SSP Charset: UTF-8 SecurityLevel: local Reference0: \0\s[0]\1\s[10]\0おはダ
SHIORI/3.0 200 OK Sender: matsuri Charset: UTF-8 Value: \0\s[0]\1\s[10]\0おはー\1らっきー\e
とりあえず、これくらいの長さの台詞ならちゃんと喋ってくれるようになってくれました。
しかし、長い台詞を表示しようとすると結局途中で切れてしまいます。
それにCROWでは相変わらず何も喋ってくれず。
まー、それは置いといて、CLANNAD AFTER第2話が放送されました。
ほんと良かった。もう毎週木曜がたのしみでなりません。
どうやら有紀寧さんシナリオもちゃんとやりそうだし楽しみ。
ただ相変わらず風子分が足りない。
1話に続いて、本来風子の出るところにことみが出てきてます。
そして、それも置いといて昨日のリリカルの続き
OnTranslateのReference0が壊れる
木曜日, 10月 16th, 2008相変わらず、11/3のうかべんに向けてCLでSHIORIを作っています。
けど、最近は現実逃避にゲームばかりやっていたので実は久しぶりというのは内緒です。
以前から、困っているのが、リクエストに対して長い台詞を送ると、
途中で切れたり、内容が壊れていたりするという現象。
しかし、長くない台詞に対しても起こるようになってきました。
リクエストとレスポンスを追いかけてみたところ、
SHIORI/3.0 200 OK Charset: UTF-8 Sender: matsuri Value: \0\s[0]\1\s[10]\0えんいー\1なんか懐かしいなそれ\w5\-
リクエストに対して、このようなレスポンスを返した際に、
次のようなリクエストがやってきました。
GET SHIORI/3.0 ID: OnTranslate Sender: SSP Charset: UTF-8 SecurityLevel: local Reference0: \0\s[0]\1\s[10]\0えむ
OnTranslateとはなんぞやと調べてみたら、こちらがValue(台詞)を返すと、
その台詞を表示する前に台詞をReference0に入れて送られるリクエストだそうです。
(ログを取ったり、台詞の語尾の置き換えたりする場合に使うそうです。)
このリクエストに対するレスポンスとしてValueを返さなければ
OnTranslateのReference0が実際に表示される内容となるみたいですが、
上記の通り内容が壊れています。
結果として「えむ」という台詞が表示されてしまいました。
以上がSSPでの動作で、CROWで試してみたところ、
OnTranslateが送られてこない代わりに、なにも喋ってくれません。
こいつは困った…
全然関係ないけど10/11のリリカルの続き
記事にクダーを付けれるようにした
水曜日, 10月 15th, 2008今更ですが、はてなスターを付けてみました。
「Add Star」を「Add Cdr」に書き換えたかったんだけど、
どうもここは触れないっぽいです。
(RSSリーダで見てる人はなんのことか分からないと思うので、直接見てくださいね。)
B Method
土曜日, 10月 11th, 2008東京から突然nishさんがやってきてBメソッドの本をくれました。
「The B Language and Method」
って、値段見たら尋常でなく高い…
『¥ 12,799より』っていくらなんでも高すぎるだろ…
そんなわけで(*)、この本は大切に扱いながら読んでいこうとおもいます。
(*) べっ、別に高いからじゃないんだからね! 譲って頂いた本だからなんだからね!!!
内容をパラパラと読んでみると、大量の数学記号が目に付きました。
どうやってキーボードから打ち込むんだと思ったら、
ちゃんとそれぞれの記号に対応した書き方があるんだとか。
(例: 『∀v.[S]P』 -> 『[@v.S]P』)
専用のエディタを使うとちゃんと数学記号の方で表示されるそうです。
とにかく記号の数がやたら多い。
ラムダ計算や論理学等を趣味でやっていたため、分かる記号も結構ありましたが、
知らない記号が沢山ありました。さすがフランス生まれの言語。
(「=」の上に「^」が乗った記号や、「(」を右に90度倒した「^」に似た記号とか。)
ということで、この秋からは頑張ってBメソッドを勉強しようかと思います。
この秋やらなければ来年の秋に。来年やらなければ再来年の秋に。再来年にやらなければ…
昨日のリリカルの続き
色々あった
金曜日, 10月 10th, 2008bugyo.tkの鯖が新しくなったそうです。
以前より速く動くようになった…気がします。
下宿の近くが実は心霊スポットだったことが発覚しました。
夜に通ることも結構あるのに一度も幽霊に会えないよ…
前に作ったCommon Lispの演算子順位構文解析のプログラムをちょっと書き足して、
自然な感じでCLに中置記法を混ぜれるようにしてみました。
(let (x y) #[ x = (y=5*(4+3)) - 2 ] (format t "~&x=~A, y=~A~%" x y)) ; "x=33, y=35"と出力される
リード時に通常の式に変換されるので、
コンパイルしたら余計時間は一切掛からない優れもの。
ただ、使い道が全くない気がします(笑)
Common LispでSHIORI作ってます。
DLLからLispプロセスを起動してパイプで通信。
とりあえず、文字くらいは表示できました。
しかし、長い台詞を表示させようとすると、なぜか途中で終わってしまいます。
(このスクリーンショットがまさにそれ。話のオチが切れてるwww)
DLL側のrequest関数の戻り値は確かに台詞の最後までデータが入っているはずなのに…
こいつは困った。
ハードディスクを漁ってたらこんなものが出てきた。
激しくリリカル。
本日京都でようやくCLANNAD AFTER STORYが始まった。
今まさに鑑賞中だけど実に非常に素晴らしい。
(以下ネタバレ注意)
オープニングが渚祭になってると思ったら、他のキャラも出てた。
本来AFTERに出てこないことみが本編にも出てきてるし、
この調子でいくと、有紀寧の出番もあるかも。
ただ、強いていうなら風子分が足りない。
草野球編に風子が出ないなんて…
それはさておき、AFTERって言ってるけど、
ゲームにおけるAFTERじゃなくてどうも、アニメ版の続きという位置づけっぽいです。
2クールあるから、一応最後までやるのかな?
本当にこれから毎週木曜が楽しみです。
VC++2008でECLのmake
金曜日, 10月 3rd, 2008ページの最後の方にmakeの一連の流れを書いてあります。
さっさとWindowsへのECLの入れ方を見たい人はそちらをどうぞ。
WindowsのDLLをCLを使って書きたいため、
CのソースにCLのソースを埋め込もうと思い、
ECLを試してみることにしました。
HDDをあさってみたら、以前ダウンロードした「ecl-0.9j.tgz」というファイルがあったので(*)、
まずそれを展開。若干古そうな気がしたのでcvs updateをかけておきました。
cygwin上でmakeしようとしたんですが、上手くいかなかったので放置していたという恥ずかしいものです(笑)
そして、Visual C++ 2008 Express Editionをダウンロード。
しかし、「Visual Studio 2008 コマンドライン」(*)を起動しようとすると、
「使い方が間違っています」
という悲しいエラーが出てきました。
環境変数を設定するバッチファイル(vsvars32.bat)を覗いてみると、
怪しげな命令があったので、適当に書き直したらちゃんと動きました。
Microsoftどうなってるんだ… Vista用の命令?
(※)インクルードパスなどの環境変数を設定してコマンドラインを立ち上げるもの
それで、ECLのマニュアルに従い、nmakeすると、何故かエラーが発生。
場当たり的に修正しながら突き進んでみたものの、途中で完全に行き詰まりました。
ここで、一旦諦めかけたんですが、もしかしてと思い、
ecl-9.0j.tgzを展開しなおして、cvs updateなど余計なことをせずにmakeしてみると成功。
なんとも悲しいオチが待っていました。
SourceForgeの方に新しいバージョンのアーカイブが無いか確認しに行くと、
ecl-0.9l.tgzというものがあったので、これをダウンロードしてmake。一発で成功しました。
恐らくこっちの方が新しいと思うのでこれを使うことに。
> ecl ECL (Embeddable Common-Lisp) 0.9i (CVS 2008-06-19 17:09) Copyright (C) 1984 Taiichi Yuasa and Masami Hagiya Copyright (C) 1993 Giuseppe Attardi Copyright (C) 2000 Juan J. Garcia-Ripoll ECL is free software, and you are welcome to redistribute it under certain conditions; see file 'Copyright' for details. Type :h for Help. Top level. > (car '(a b c)) A >
疲れたので今日はここまで。
起動時に「0.9i」と出てるのが少々気になるけど、あえて気にしないことに。
* Windows XP上でのECLのmake方法まとめ *
1. Visual C++ 2008 Express Editionをダウンロード及びインストール
2. C:\Program Files\Microsoft Visual Studio 9.0\Common7\Tools\vsvars32.batを以下のように変更
* 変更前 * call :GetWindowsSdkDir if not "%WindowsSdkDir%" == "" ( set "PATH=%WindowsSdkDir%bin;%PATH%" set "INCLUDE=%WindowsSdkDir%include;%INCLUDE%" set "LIB=%WindowsSdkDir%lib;%LIB%" ) * 変更後 * rem call :GetWindowsSdkDir set WindowsSdkDir=C:\Program Files\Microsoft SDKs\Windows\v6.0A\ rem if not "%WindowsSdkDir%" == "" ( set "PATH=%WindowsSdkDir%bin;%PATH%" set "INCLUDE=%WindowsSdkDir%include;%INCLUDE%" set "LIB=%WindowsSdkDir%lib;%LIB%" rem )
3. ECLのアーカイブをダウンロード及び展開
4. スタートメニューから「Visual Studio 2008 コマンドライン」を起動。以下のコマンドを入力
cd (ECLの展開先)\msvc nmak nmake install prefix=(インストール先(ディレクトリは勝手には作られません))
当然のことながらファイルパス等は適宜修正してください。
自分のPCでしか試していないので、他のWindows XP環境で上手くいくかは不明です。
というか、VC++のバッチファイルは普通に考えたら触らなくてよさそうなんだけど…
Lispで演算子順位構文解析
水曜日, 10月 1st, 2008 夏休みが終わってしまいました。
そして同時に前期の成績が発表されました。
春先に「単位が足りなくい」という恐ろしくリアルな夢を見ましたが、
どうやら無事に4年生に進むことは出来そうです(4年で卒業出来るかはまだ分かりません(笑))。
という訳で(?)Lispで演算子順位構文解析を行うプログラムを書きました。
工夫した点はマクロを使って予め優先順位のテーブルをコードに展開したこと。
キャッシュのことを考えたら展開した方が遅いかもしれませんが、それは気にしない方針で。
あと、手を抜いた点はストリームからの読み込みはread関数を使ったこと。
演算子に大して何もしないリーダマクロ関数を設定して楽をしてます。
「マイナス」と「引く」を区別できない気もするけど、それも気にしない方針で。
(def-op-parser test-parser (input stack acc) () (((#\+ 1 :left) (let ((x (pop acc)) (y (pop acc))) (push `(+ ,y ,x) acc))) ((#\* 2 :left) (let ((x (pop acc)) (y (pop acc))) (push `(* ,y ,x) acc)))) ((( #\( #\) ) )))
まず、def-op-parserというマクロを使ってパーサ関数を定義。
第1引数は作成する関数の名前、第2引数は後で使う変数の名前。
第3引数はリテラルに対する操作(今回はなし)。
第4引数は演算子とその優先順位、結合性、還元時の操作。
第5引数は括弧とその還元時の操作(今回はなし)。
そんで、これを使ってみたらこんな感じです。
OP-PARSER> (with-input-from-string (s "(1+2*3+4)*5+6*7") (test-parser s)) (+ (* (+ (+ 1 (* 2 3)) 4) 5) (* 6 7))
なんか上手くいってるっぽい。やったね。
▲完成したときの心境
で、うかべんまで残り1ヵ月程となってしまいましたが、ネタの方が全然出来てません。
そろそろペースを上げてものを作っていかないと…
この構文解析も里々のパースの為に作ったものです。
それにしても、里々って、Lispの様に括弧を使って関数呼び出し等を行う言語なのに、
算術式において優先順位の為に括弧を使うってどうなんだろう…
半角と全角で区別って言うのは流石にかっこ悪い気がする…