プログラミングGauche

評価モデル

計算の様子を理解するためにはどうすればいいだろうか? 計算機で実際に動かす 何をやってるかは分かるだろうけど、ある特定のプログラムに関してしか使えない方法だ。計算一般で使えるような方法はないか? 機械語を追って計算機をシミュレート あまりにも…

置き換えモデルと副作用

置き換えモデルでは、副作用がある式を扱えない場合があるらしい。まず「副作用」を定義しなくちゃいけないだろうけど、自分もちゃんと理解できていないので定義せずスルーする。ごめんなさい。では、置き換えモデルで (((lambda (y) (lambda (x) (begin (se…

置き換えモデル

「名前」と「名前に紐づけられた値」のペアを束縛という。 ある時点での束縛は複数あることが普通。ここでは piが3.14に fooが42に barが"hello"に 束縛されているとしたら、 名前 値 pi 3.14 foo 42 bar "hello" みたいな表になる。これを環境と呼ぶ。束縛…

例外その2

今回はGaucheのtest*、test-start、test-endの簡易版を実装してみようという内容。 今までの知識を以ってすれば特に難しくはないが、簡易版test*であるmytestの実装でのthunkの話がポイントですかね。 手続きの評価を遅らせるために、関数適用ではなくラムダ…

例外その1

10章のうち、後半の例外について。まず、他の言語との概念の違いについて。Schemeには例外に関係する用語として以下のようなものがある。 例外:例外的な事象のこと。 コンディション:例外が発生した時に作成される、例外の状況を記述するためのオブジェク…

テスト

10章「テストと例外処理」のうち、テストに関する箇所をば。 手続きtest* ちなみに、test* は以下でも出てきた。 id:yagiey:20090307:1236410685 id:yagiey:20090321:1237653683 評価結果が○○と等しくなるはずだ!ってな感じで、次のように使う。 gosh> (use…

9章おしまい

9章の最終節、8節「グラフ」。 今までプレイヤーのHPやら持ち物を操作する手続きを作ってきた。 その中に、現在位置を更新する手続きset-position!も定義してみたが、positionが保持する値の意味は規定していなかった。 ということで、positionを使って、動…

名前をまとめる何か

item-properties item-property-get get-player-attr update-player-attr! たった4つの手続きなのに、もうだめだ。 全ての名前が平等で、のっぺりとしたイメージが気持ち悪い。 クラスや名前空間など、名前をまとめる何かが欲しくなるな。 じゃぁ、作れば?…

準クォート

リテラルデータに手続きを埋め込むにはちょっとした工夫が必要です。 ということだが、手続きに関わらず、評価済みの値を埋め込む場合一般的に言える話ですな。 gosh> (define foo '(hoge . (lambda (n) (+ n 1)))) foo gosh> foo (hoge lambda (n) (+ n 1))…

多値をreceiveで受け取らなかったら

114ページからの「手続きによるパターンの抽象化」を読み返しているとき、ふと不思議に思ったことがある。 それは、手続きtraverseを使ったmember2の定義内での、valuesの使い方。 ;; traverseを用いない (define member2 (lambda (elt lis . opt) (let-opti…

delete-1

さて、半年つんどくしていました「プログラミングGauche」。 続きからやろうと思ったら「今まで何やってたっけ?」っていう感じだったので、9章の始めからつらつらと読んでた。 で、つまずいてたdelete-1のnon-copyバージョンを書いてみると、割とすらすらと…

ここらでひと息

もうすぐ9章がおわる。 章の見出しから判断すると、今後の話題で僕が一番興味を引かれるのは11、18、19章だなぁ。 11章はThe Little Schemerの10章と関連する話題のような気がする。 「プログラミングGauche」は、SICPを読むに当たってSchemeの初歩的なこと…

一般化set!、その2

確か、121ページまで終わってたはず。 9章6節、「リストの変更と一般化set!」の続き。 HPの取得と変更は、get-itemとadd-item!にならって、次のように書ける。 ;; HPの値を取得 (define get-hp (lambda (player) (cdr (assoc 'hp player)))) ;; HPの値を変更…

わかった!...かな?

id:yagiey:20090322:1237738147でpush!後に持ち物リストが更新されないことが理解できなかったけど、トラックバックもらって分かった。 id:SaitoAtsushi:20090323:1237790745 まず、例えば、持ち物がpotion、dagger、cookieだったら (assoc 'inventory playe…

add-item!

指定したプレイヤーの持ち物に、指定したアイテムを追加する手続きadd-item!。 答えを見ずに書いたら間違えた。 ;; アイテムを追加する (define add-item! (lambda (player item) (let ((items (cdr (assoc 'inventory player)))) (push! items item)))) 使…

has-item?

さて、9章6節の後半。 make-player(id:yagiey:20090314:1237041715)で作った値で大域変数*player*を束縛しといて、*player*をいろいろ変更していく。 まず、指定したプレイヤーが指定したアイテムを持っているかどうか調べるhas-item? (define has-item? (…

delete-1を名前付きletで書き直し

やってみた。 gosh> (use gauche.test) #<undef> gosh> (define delete-1 (lambda (elt lis . options) (let-optionals* options ((cmp-fn equal?)) (let loop ((lis lis)) (cond ((null? lis) lis) ((cmp-fn elt (car lis)) (cdr lis)) (else (let ((tail (loop (c</undef>…

リテラルデータの破壊に注意

9章5節のコラム「リテラルデータの破壊に注意」。 Schemeの仕様では、リテラルデータを変更することは許されていないそうだ。 gosh> (define *nums* '(1 2 3 4 5)) *nums* gosh> (set! (car *nums*) 0) ; やっちゃだめ。 #<undef> gosh> *nums* (0 2 3 4) ってやる</undef>…

一般化set!

9章6節。最近は1日1節にも満たないなぁ。 超スローペース。こりゃいかん。 id:yagiey:20090307:1236410958で登場したset!が再び登場。 set!は既に束縛されている名前を別のオブジェクトに束縛し直す手続き(?マクロ?よく分からんけど)だったけど、SRFI-17…

push!マクロ

9章1節で出てきたけど、ガン無視してた。 先頭に要素を追加したリストで名前を束縛し直す操作 gosh> (define *nums* (list 1 2 3 4)) *nums* gosh> *nums* (1 2 3 4) gosh> (set! *nums* (cons 0 *nums*)) (0 1 2 3 4) みたいなのはよくあることなので、push…

matchでのエラー処理

はい、まだまだ9章5節。 依然としてmake-playerは奇数個の引数を受け付けない。 「奇数個の引数に適用することを受け付けない」というのは無理だけど、せめてもう少しわかりやすいエラーメッセージを出したい。 ということで、matchで全てのパターンにマッチ…

名前付きlet

9章5節。名前つきlet。 今回はRPGを想定して、以下のようなプレイヤーの状態をを表す連想リストを規定してみる。 ((hp . 320) ; 体力 (mp . 66) ; 魔力 (position . #f) ; 現在位置 (inventory potion potion dagger cookie dagger) ; 持ち物 ) 「ポーション…

連想リストふたたび、ふたたび2

めっちゃ嘘ついてた。 ってか、それ以前に、has-item?(id:yagiey:20090307:1236410294)とdelete-item!(id:yagiey:20090307:1236410958)は使っちゃダメだよね。 だって*inventory*から消してしまうし。 連想リストふたたび、ふたたび 違ぁぁぁーう!! どう…

連想リストふたたび、ふたたび

まだ9章4節。 id:yagiey:20090310:1236690209のデータベースから、値を取り出すための手続きを作ってみる。 (define item-properties (lambda (item) (cond ((assoc item *item-database*) => cdr) (else '())))) (define item-property-get (lambda (action…

連想リストふたたび

9章4節。 連想リストをネストさせて簡易データベースを作ろう、と。 データベースとは、 データベース = ((アイテム1 . アイテム1の性質) (アイテム2 . アイテム2の性質) ・・・ (アイテムn . アイテムnの性質)) アイテムの性質 = ((属性1 . 値) (属性2 . 値…

手続きによるパターンの抽象化

9章3節。 id:yagiey:20090309:1236597268の最後で挙げた3つの手続きは、以下の共通部分を持つ。 (lambda (elt lis . optionals) (let-optionals* optionals ((cmp-fn equal?)) (define loop (lmabda (lis) (cond ((null? lis) ○○) ((cmp-fn elt (△△ lis)) (□…

連想リスト

9章2節、連想リスト。 キーと値のペアで保存しといて、キーを元に値にアクセスするアレ。 多くのスクリプト言語などにも、連想配列という形で実現されてたりするな。 Schemeではキーと値のペアをドット対で表現し、連想リストをドット対のリストとして表現す…

サポートページ

プログラミングGaucheのサポートページに模範解答があるじゃないっすか! delete-1の解答をみてみると、結構違うじゃーん。 >< 模範解答 (define (delete-1 elt lis . options) (let-optionals* options ((cmp-fn equal?)) (define (loop lis) (cond [(nul…

set!

既に束縛されている名前を、再び違うオブジェクトに束縛する手続き。 多くの手続き型言語でいう「代入」をやりたいときに使う。 gosh> (set! lambda 3.141592) 3.141592 gosh> lambda 3.141592 みたいな。 これやっちゃうと大変なことになるけどね! で、指…

9章1節の練習問題:delete-1

srfi-1のdeleteは等価述語を満たす要素を全部削除してしまうけど、見つけた1つ目だけ消す手続きdelete-1を定義してみると (define delete-1 (lambda (elt lis . optional) (let-optionals* optional ((cmp-fn equal?)) (define loop (lambda (lis) (cond ((n…