ニコ動Lisp 2.0[lambda始動]

5月 28th, 2008

ニコニコ動画のメンテナンスが終わったので、ニコ動Lisp2.0(仮称)が始動しました。

「もっと評価されるべき」タグが付いていたので、文字アトムも評価することに。
もっと評価されるべきの意味が違うという突っ込みもありました。
期待通りの突っ込みをありがとうございます。
それはともかくスクリプトを更新して1分もしないうちに
「ラムダきたー」というコメントが書き込まれたんですよ。
どれだけlambdaが欲しかったんだwwww
まあ、なにはともあれ、lambdaが無事動いてよかった。
普段から「lambdaかわいいよlambda」とお思いの諸兄も安心してニコニコできますね。

prognとかdefunとかLisp的(NOT Scheme的)なスペシャルフォームを持っていますが、
lambdaに関してはScheme的な評価規則となっています。
CommonLispでは次のような式は動作しません。

(((lambda (x)
(lambda (y)
(+ x y)))
3)
4)

というのも、関数適用の第一要素はシンボルか(lambda …)に限られているためです。
一方、Schemeではこの式は正しく動作します。
Schemeでは手続き呼び出しの第一要素を評価したものを手続きとして扱い、その形は問わないからです。
ニコ動LispもこのSchemeの規則に従っています。
そのため、上記式は問題なく動きます。

ニコ動Lispはセル、スタックを自分で管理しているので、
本当はGCを書かないといけないんですけど、サボって書いていません。
評価しすぎると大変なことになるのでご注意を(笑)
……いま気づいたんですが、スタックを自分で管理してるってことは、
call/ccも結構簡単に書けますね。頑張れば。
でも、あまりにソースが汚いので頑張る気は起きません(笑)

あの巫女の絵は誰が描いたのかという質問があったので回答。
あれは私の兄が書いたものを無断で使用しました。
以下私と兄のメールでのやり取り。
zick:
前の一恋とクルルの絵を無断で使わせてもらうよ!
(↑こういった時点で無断じゃなくなったやったね(笑))
兄:
お前・・・・頭、いいな・・・

ニコ動Lisp 2.0[予告および仕様]

5月 28th, 2008

ニコニコ動画で動作するLispインタプリタですが、
ついにlambdaとdefunが完成しました。
もちろん再帰呼び出しも可能です。

(defun f (x) (if (eq x 0) 0(+ x (f (- x 1))))) (f 3)

こんなコードが動きます(ただし、2回に分けて入力してください)。
で、ちゃんとテストもしたし、これで完成だと思い、
確定ボタンを押したんですが、なぜかニコニコ動画から反応が返ってこない。
何回試しても反応が返ってこない。
一旦ログインからやり直してみるかと思い、ログアウトしようとしたら、

メンテナンスのお知らせ
現在ニコニコ動画はメンテナンス中です。
5月28日(水) 13時00分~16時00分(予定)
※都合により変更となる可能性がございます。

ぎゃああああああああああああああああ
ちなみに、スクリプトの確定ボタンを押したのは13時を5分ほど回ったときでした(泣)

**ニコ動Lisp 2.0 仕様**
サポートする関数:
car
cdr
cons
eq (数の比較もこれで行う)
atom
+ (引数は任意個)
– (引数は2つ)
サポートするスペシャルフォーム:
quote
if
progn
lambda
defun
データ:
文字アトム (日本語なども使用可能)
数アトム (入力時は非負整数のみ)
コンス (今のところはimmutable)
注意点:
ドット記法による入力は受け付けない。すなわち、 ‘(a . b) は正しい式として扱われない
セルの数は512個固定であるが、GCは行われない。
0.5秒に1回の処理を行うため、再帰呼び出しを繰り返し使うような式は動画の時間内で評価が終わらない可能性がある。
バグと思われるものがあったら報告してもらえると嬉しいです。
ただし、修正されるまではそのバグは仕様です(笑)

続・ニコ動でLisp

5月 27th, 2008

昨日の動画に書き込まれたコメントを見てみたら、
(+ 1 2) とか (print “hoge”) といった書き込みが多数ありました。
pure lispっていったのに……
特に前者のような数値演算をする式があまりにも多かったので、
急遽、数アトムと+をつくり、ついでにifやprognも作っておきました。
少し気になったので、コメントを
・リスト操作
・数値演算
・printを使用
の3つに分類してみたところ、以下のような結果になりました。
(複数に分類されたり、どれにも分類されなかったものもあります。)
・リスト操作: 32%
・数値演算: 47%
・printを使用: 20%
ちなみに、この集計を取ったのは、数アトムと+を作った後ですが、
半数のコメントはこの改造前に書かれていたものでした。
ちゃんと評価できた式は50%前後といったところでしょうか。
数値計算はともかく、20%もの人がprintを使ったというのが驚きです。
(まあ、よく分からない人が他の人のまねをして、
その結果printが量産されたとも考えられますが。)

話は変わりますが……
ジュンク堂に行ったら、オライリーフェアとかなんとかで、
コースターがもらえました。ヒトデのやつ。
ヒトデのコースターといえば、以前CLANNADのDVDの初回特典に
ついてきたものがあったので、せっかくなので並べてみました。
ヒトデ
今日はヒトデ祭りだぞ!

ニコ動で動作するLispインタプリタ書いたよ

5月 26th, 2008

どうもzickです。
2/1に見た夢をきっかけに触り始めたニコスクリプト(正確にはニワン語というらしい?)ですが、
しばらく触っていないうちに色々と機能が追加されており、なんと手続きが作れるようになっていました。
知らない機能を色々触っていたら、いつの間にかLispインタプリタが出来上がっていました。

2/1に見た夢が4ヶ月ほどを経て正夢になってしまいました。
関係ありませんが、少し前に単位が足りなくて4年生になれない夢を見ました。
こちらの夢は正夢にならないことを祈るばかりです。

*ニワン語メモ*
大体のことはニコニコ動画まとめwikiを見れば分かります。
(Lispインタプリタを半分くらい作ってからここの存在に気づきました。もっと速くググればよかったorz)
とりあえず、ここに載っていないような細かい事項を書いておきます。
[1行の制限]
スクリプトは1行に1024文字まで書くことができます(以前はもっと短かった気がします)。
手続きを作って処理を分割できるので、この制限はあまり問題ないでしょう。
[文字列]
文字列に str[n] のように添え字をつけるとn文字目(0から始まる)の文字が得られます。
一見C言語のようですが、正確にはn文字目の文字のみから成る文字列が得られます。
その文字列自身ではなく恐らくコピーが得られるので文字列はimmutableです。
また、文字列のメソッドindexOfは以前は1引数の関数でしたが、
いつのまにか2引数の関数になってました。詳しくはまとめwiki参照。
[配列]
arr=[1,2,3,4,5] のように大括弧で囲むと配列を作ることが出来ます。
大きな配列を作りたかったら要素を沢山書いたらいいのですが、
要素数を100個ほどにすると動作しません(50個では動作しました)。
配列の要素に配列を入れることができるので、大きな配列が必要な場合はこれを使うのも手です。
(push, shiftを使って動的に配列を大きくした場合どうなるかは未確認です)
[手続き]
再帰呼び出しが可能です。その場合も引数$nが壊れることはありません。
これでループが書けます。恐ろしく便利です。

NScLisperでSHIORI

5月 13th, 2008

先に結論を書いておきます。
以下のものは全く役に立ちません(笑)

SWI-Prologのcoroutining

5月 10th, 2008

SWI-Prologのマニュアルを読んでいたら、面白そうな述語を見つけました。

6.2 Coroutining
Coroutining deals with having Prolog goals scheduled for execution as soon as some conditions is fulfilled. In Prolog the most commonly used conditions is the instantiation (binding) of a variable. Scheduling a goal to execute immediately after a variable is bound can be used to avoid instantiation errors for some built-in predicates (e.g. arithmetic), do work lazy, prevent the binding of a variable to a particular value, etc. Using freeze/2 for example we can define a variable can only be assigned an even number:

?- freeze(X, X mod 2 =:= 0), X = 3
No

( http://gollem.science.uva.nl/SWI-Prolog/Manual/coroutining.html )


freezeは第一引数に未束縛の変数を指定し、
第二引数に『第一引数の変数が束縛されたときに実行されるゴール』を指定します。
上の例ではXが3に束縛された時点で X mod 2 =:= 0 が実行されます。
とりあえず、使ってみました。

?- [user].
test(Y):- write(1), freeze(X, (write(a),Y is X + 1,write(b))), write(2), X = 3, write(3).
?- test(Y).
12ab3
Y = 4;
no

実行順序はこんな感じ。
1) write(1) が実行 (画面に1が出力)
2) freeze(X, (write(a),Y is X + 1,write(b))) が実行 (引数は評価されない)
3) write(2) が実行 (画面に2が出力)
4) X = 3 が実行
5) Xが束縛されるのをきっかけにfreezeの第二引数が実行される
5a) write(a) が実行 (画面にaが出力)
5b) Y is X + 1 が実行
5c) write(b) が実行 (画面にbが出力)
6) write(3) が実行 (画面に3が出力)
私自身はコルーチンについてはあまり知らないんですが、
これはむしろ変数の束縛をトリガとした遅延評価みたいに感じました。
Schemeのdelayがfreezeに対応して、forceが変数の束縛に対応する感じです。
他にもfrozenという述語があり、これは指定された変数をトリガとしている
freezeオブジェクト(?)を取得できます。

?- freeze(X, write(a)), frozen(X, Y).
X = _G397{freeze = user:write(a)},
Y = user:write(a) ;
No

使い道は現在はいまいち分かってません。
他にもcoroutining関連の述語はいくつかありますが、
それらはまたの機会にでも。
(条件を満たしたときに引数の実行を始めるwhenという述語があるんですが、
なぜか上手くいかなかったorz)

Prologで毒電波

5月 6th, 2008

リファラを辿って行ったら素敵なサイトを見つけました。
うかべん 伺的ソフトウェア勉強会統合作戦本部公式情報サイト
伺か関連の勉強会なんてものがあったんですね。
しかも5/5に大阪で開催してたとか。
もっと早く知ってれば参加したのに orz
とりあえず、何かやっておこうと思い、
やっつけですが、Prologで毒電波を飛ばしてみました。
(製作時間3分ほどwww)
Prologで毒電波
よし、なんだかよく分からないけど上手くいったぞ(笑)

やる夫が自転車で琵琶湖を一周したそうです

5月 5th, 2008

それはそれは昨日のお話でした……

# 5月3日
     ____     
   /      \     
  /  ─    ─\    ”ごーるでんうぃーく”という時期なのに、
/    (●)  (●) \   なんだか全然ゴールデンな気がしないお……
|       (__人__)    |   授業に出ないのは普段も同じだけど、
/     ∩ノ ⊃  /    とりあえずなにか連休らしいことでもやってみるお
(  \ / _ノ |  |  
.\ ”  /__|  |  
  \ /___ /
       ____
     /⌒  ⌒\
   /( ●)  (●)\    そうだ琵琶湖行こう!
  /::::::⌒(__人__)⌒::::: \   
  |     |r┬-|     |
  \      `ー’´     /
# 5/4
[午前3:00]
       ____
     /⌒  ⌒\    ちょっと早すぎる気もするけど、
   /( ―)  (―)\   涼しくて交通量の少ない朝を有効に利用するためには
  /::::::⌒(__人__)⌒::::: \ これくらいの時間に起きたほうがきっといいはずだお。
  |              |  
  \               / 
[午前3:20]
       ____
     /⌒  ⌒\     朝食と荷物の準備、それから
   /( ●)  (●)\    玄関に置いてあるリリカルLispの在庫に
  /::::::⌒(__人__)⌒::::: \  朝の挨拶を済ませていよいよ出発だお!
  |     |r┬-|     |  
  \      `ー’´     / 
在庫
▲玄関に置いてあるリリカルLispの在庫
[午前3:40]
         ____
        /\  /\
      /( ●)  (●)\
     / :::::⌒(__人__)⌒:::::\ 
     |     |r┬-|       | 
     \     ` ー’´     /
     /          \
      | ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ |  トン
   _(,,) というわけで    (,,)_
  /  |  ここでコース紹介 .|  \
/    |              .|    \
    .|__________|

まず、烏丸通を五条まで下り、そこから東に向かい1号線に沿って山科を経由して大津へ。
浜大津駅を見つけたら、あとは琵琶湖に沿って適当に走るだけ。
今回は右回り(時計回り)で回ることに。
琵琶湖一周をする際には普通は唐橋という場所を基点にするんですが、
今回はそこから5kmほど北にある北大津駅を基点にしました。
GoogleMap

五条
▲五条烏丸
[午前4:00]
        ____
       /      \!??
      /  u   ノ  \     ここはどこだお
    /      u (●)  \
    |         (__人__)|
     \    u   .` ⌒/
1号線を走っていたら途中で歩道がなくなり、
朝ではあったものの交通量も多かったため
1号線を避けようとしたところ、見事に迷いました。
必要以上に坂を上った気がします。正直失敗でした。
       ____
     /      \    ああ・・・街の光が遥か下に見えるお……
   /  _ノ  ヽ、_  \   きっとあれこそが山科の光だお。
  /  o゚⌒   ⌒゚o  \  あの街の光に向かってDASHだお!
  |     (__人__)    |  
  \     ` ⌒´     /
こうしてなんとか1号線に復帰。
しかし、学習能力のないやる夫は、
またもや同じ失敗をしてしまうのでした。
[午前4:30]
       ____
     /      \
   /  _ノ  ヽ、_  \   こんどは訳のわからない砂利道だお……
  / o゚((●)) ((●))゚o \  自転車がパンクしないか心配だし、
  |     (__人__)    |  そもそも標識も何もないから
  \     ` ⌒´     /  ちゃんと1号線に戻れるかもわからないお……
その後なんとか1号線に復帰。
しかし、無駄に坂ばかり上ったためか、
早くも疲れはじめました。
     ____     
   /      \     
  /  ─    ─\    結構自転車こいだのに、
/    (●)  (●) \   いまだに滋賀県に着かないとは
|       (__人__)    |   一体どういうことだお……
/     ∩ノ ⊃  /  
(  \ / _ノ |  |     実は「滋賀県」や「琵琶湖」の存在って
.\ ”  /__|  |      都市伝説かもしれないお。
  \ /___ /
そんなことを考え始めたとき、
やる夫の目に一つの標識が飛び込んだ。
大津
▲多分大津市って書いてあるよ
           ____
       /::::::::::::::::\
      /::::::─三三─\
    /:::::::: ( ○)三(○)\  
    |::::::::::::::::::::(__人__)::::  | いつの間にか滋賀県にはいっていたお!!!
     \:::::::::   |r┬-|   ,/  (きっと変な砂利道を通ってるうちに、
    ノ::::::::::::  `ー’´   \  県境を越えていたんだお……)
  /:::::::::::::::::::::            
 |::::::::::::::::: l  
[午前4:50]
しばらく自転車をこぎ続けると市街地に。
このときの気温は15度。
非常に快適でした。
15度
▲「これより13キロ15℃」に見えるのは気のせい。
[午前4:55]
浜大津駅に到着。
このあたりでしばらく琵琶湖を見つけるために彷徨う。
浜大津
▲側面から見た浜大津駅。正面はもっと立派。
[午前5:00]
       ____
     /⌒  ⌒\      ついに琵琶湖を発見したお!
   /( ●)  (●)\     その存在は都市伝説じゃなかったんだお!
  /::::::⌒(__人__)⌒::::: \   (小中高学校全ての遠足で一度は琵琶湖に
  |     |r┬-|     |   行った気もするけど気のせいだお)
  \      `ー’´     /
琵琶湖
▲適当な橋の上から撮影した恐らく琵琶湖らしきもの。
[午前5:50]
      ____
     /⌒  ⌒\      
   /( >)  (<)\     琵琶湖大橋の西詰めに到着!
  /::::::⌒(__人__)⌒::::: \    傍の観覧車に「貸土地」って書いてあって、
  |    /| | | | |     |    どことなく殺風景だったお
  \  (、`ー―’´,    / 
琵琶湖大橋西詰め
▲琵琶湖大橋西詰め。このときの気温は15度。
[午前6:00]
その後、161号線をひたすらに北上。
右手側に琵琶湖が見えるはずなのに、
建物が結構あってあまり見えませんでした。
そして何故かコンビニが異常に多かった。
しばらくして「琵琶湖レイクサイド自転車道」とやらを発見。
『湖』と『レイク』って意味が被ってないかなどと気にしつつも、
利用させていただくことに。
とまあ、ここまでは道に迷いつつ、写真を撮りつつ、
観光気分でのんびりと進んでいたわけなんですよ。
しかし、このペースで回っていて、
ちゃんと一日で変えれるのかという不安も出てきました。
少しスピードを上げようと思ったものの、
早くも足に疲れが出てきました。
運動不足恐るべし。
[午前8:00]
信号待ちをしていると、マウンテンバイクに乗ってヘルメットをした、
いかにもサイクリングをやってますみたいな集団に出会いました。
小中学生程度の子どもが半数を占めているため、
そんなにはスピードを出さないだろうとは思いつつも、
道を譲り、先に行ってもらいました。
       ____
     /⌒  ⌒\     集団の後ろの連中は遅いお
   /( ―)  (―)\    キチンと付いていかないと。
  /::::::⌒(__人__)⌒::::: \ 代わりにやる夫が列に入るお
  |              | 
  \               / 
自転車集団というものは車道を通るため、列を成します。
大学生くらいの集団なら、ぴしっと隙間なく列を作るんですが、
どうもこの集団は子どもが多かったため、隙間だらけでした。
ちなみにやる夫は自転車で長い列を作った経験はありませんが、
高校の陸上部時代にはぴしっと列を成して走る練習を散々したため、
人の真後ろを隙間なく走るということにはなれていました。
       ____
     /⌒  ⌒\
   /( ●)  (●)\     少しずつ抜いていったら集団の先頭が見えてきたお
  /::::::⌒(__人__)⌒::::: \   さすがに先頭は結構早いお
  |     |r┬-|     |   しかしこのスピード……
  \      `ー’´     /
━━━━━━━━━━━━━━━━━━━━
  .キッ!   / \   / \ 勝てるお!
___∧,、 /  (●)  (●)  \____
 ̄ ̄ ̄`’` |    (__人__)    | ̄ ̄ ̄ ̄
━━━━━━━━━━━━━━━━━━━━
列に混じって自転車をこいでいるうちに、
陸上部時代を思い出したのか、何故か闘争心に火がつき、
徐々にスピードを上げ、集団の先頭を追い越してしまいました。
しかし、その集団も恐らく琵琶湖の周りを回ろうとしているはず。
途中でやる夫がスピードを落とすとまた抜かれる訳です。
それは恥ずかしい。
そんなわけでスピードを維持したまま走行。
少し前に
『早くも足に疲れが出てきました。』
とかいってたのに不思議なものです(笑)
[午前8:15]
おなかが減ってきたので第二の朝食(第一の朝食は朝3時)。
座れる場所を見つけてそこでおにぎりを食べる。
すると、先ほどの集団に追い抜かれました。
食後のお茶を飲んでいると(恐らく)集団の一番後ろにまで抜かれました。
ここでまた何故か闘争心に火がつき、集団を追跡。
そして、再び追い抜き。
むしろかっこ悪い(笑)
親切なことに、琵琶湖の周りの道には
琵琶湖一周をする人のための唐橋を基準とした距離表示が5km間隔くらいにあり、
非常に重宝するんですが、その距離表示によると
時速20km以上を安定して出せていたようです。
       / ̄ ̄ ̄\
     / ─    ─ \    でも時速20kmって1km3分のペース。
    /  <○>  <○>  \.  高校時代なら1~2km程度なら
    |    (__人__) し  |  これより速く走れたと思うと複雑だお……
    \    ` ⌒´    /   
    /              \
[午前10:00]
分かれ道がありました。
左は山に向かって登っていく道。
右は下り道。
琵琶湖は右手側にあります。
分かれ道
▲分かれ道。左は上り坂になっています。
      ____
    /_ノ   ヽ_\
   /( ●) ( ●)\    どう考えても右の道が正解だろ。
 / ::::::⌒(__人__)⌒:::::\  常識的に考えて。
 |        ̄      |
 \              /
しかし、右の道に行ってしばらくすると行き止まり。
近くにいた方に道を聞いてみることに。
       ____
     /⌒  ⌒\    
   /( ●)  (●)\   琵琶湖沿いを走りたいけど、
  /::::::⌒(__人__)⌒::::: \ こっちにきたら行き止まりだったお。
  |     |r┬-|     |  道を教えて欲しいお。
  \      `ー’´     /
          ,. -‐’ニ、⌒` ‐ 、_
        /   ⌒`’⌒ -‐ `-、
       /  /        ヽ \
        ,’   / / / / ,       \
        .i l / / / i. _/ 〃 / ,l  l  ヽヽ
      l | ! .l-l‐|.7フl // ,〃./、|  l.   i、`,
       リ| l.、l .l’_L-=レ/ /ノノノヽ l. i  !V
       !l {fj |.|´|f;;j|!’  ´ ィi}ヽノノノ.ノ .ノ
       Nヽ.N -‘ー   , liソ∠ノノ ‘ ´    ああ、琵琶湖一周。
           !ヽ\      -  /         西のほうから来たんですか?
            ,.i!、 ` 、_ . ‐ ´              
        /  `  、! 、
        〈_      /ハ∧
       / `丶、 .//ヽ`i`,
      /  `丶、 `´   :ト、
       /           ヽヽ
     {/`丶、       ヽヽ
      ! ヽ  ヽ.       ヽヽ.
       / ̄ ̄ ̄\
     / ─    ─ \    (さも当然のように「ああ、琵琶湖一周」って……
    /  <○>  <○>  \.  実は滋賀県では自転車で琵琶湖一周は
    |    (__人__) し  |  メジャーなスポーツだったりするのかお?)
    \    ` ⌒´    /  ああ、西からだお。 
    /              \
          ,. -‐’ニ、⌒` ‐ 、_
        /   ⌒`’⌒ -‐ `-、
       /  /        ヽ \
        ,’   / / / / ,       \
        .i l / / / i. _/ 〃 / ,l  l  ヽヽ
      l | ! .l-l‐|.7フl // ,〃./、|  l.   i、`,
       リ| l.、l .l’_L-=レ/ /ノノノヽ l. i  !V
       !l {fj |.|´|f;;j|!’  ´ ィi}ヽノノノ.ノ .ノ
       Nヽ.N -‘ー   , liソ∠ノノ ‘ ´ ここをまっすぐ行ったら
           !ヽ\      -  /      分かれ道があるから、
            ,.i!、 ` 、_ . ‐ ´           展望台に向かって坂を上る道があるから、
        /  `  、! 、         それを登って途中で8号線に行けばいいです。
        〈_      /ハ∧        本当は湖沿いをいけたらいんんだけど、
       / `丶、 .//ヽ`i`,       ここは山を通る道しかないんです。
      /  `丶、 `´   :ト、
       /           ヽヽ
     {/`丶、       ヽヽ
      ! ヽ  ヽ.       ヽヽ.
       ____
     /⌒  ⌒\
   /( ●)  (●)\     (さっきの別れ道のことだお)
  /::::::⌒(__人__)⌒::::: \   分かった。
  |     |r┬-|     |   ありがとうだお。
  \      `ー’´     /
          ,. -‐’ニ、⌒` ‐ 、_
        /   ⌒`’⌒ -‐ `-、
       /  /        ヽ \
        ,’   / / / / ,       \
        .i l / / / i. _/ 〃 / ,l  l  ヽヽ
      l | ! .l-l‐|.7フl // ,〃./、|  l.   i、`,
       リ| l.、l .l’_L-=レ/ /ノノノヽ l. i  !V
       !l {fj |.|´|f;;j|!’  ´ ィi}ヽノノノ.ノ .ノ
       Nヽ.N -‘ー   , liソ∠ノノ ‘ ´    ……疲れますよ。
           !ヽ\      -  /         (ぼそり)
            ,.i!、 ` 、_ . ‐ ´              
        /  `  、! 、
        〈_      /ハ∧
       / `丶、 .//ヽ`i`,
      /  `丶、 `´   :ト、
       /           ヽヽ
     {/`丶、       ヽヽ
      ! ヽ  ヽ.       ヽヽ.
来た道を引き返すというのはあまりいい気分ではありませんでしたが、
西と東どちらから来たのか聞かれたということが、
自分が琵琶湖の北側にいることが実感できて嬉しかったため、
元気よく、道を引き返していきました。
そう、最後に聞いた言葉の意味など深く考えずに。
先ほどの分かれ道にもどり、左の道へ。
この道は奥琵琶湖パークウェイという名前が付いており、
一方通行となっているため、結構安全なようです。
10時のおやつ(?)として、ウィダーinゼリーを飲み、
気合を入れて坂を上り始めました。
       /      \
      /ノ  \   u. \   ずっと上り坂だお……
    / (●)  (●)    \  しかも気温も上がってきて熱いお……
    |   (__人__)    u.   |
     \ u.` ⌒´      /
本当にずっと上り坂でした。
おまけに気温も最初の15度からずいぶん上がり24度。
かなり苦しかったです。
奥琵琶湖パークウェイ
▲奥琵琶湖パークウェイからみた風景
       /      \
      /ノ  \   u. \   すこし前に通った道が遥か下に見えるお……
    / (●)  (●)    \  いつになったら下りになるんだお……
    |   (__人__)    u.   |  気合と根性だけで登り続けるのも
     \ u.` ⌒´      /  いつまでもつか分からないお……
[午前10:30]
登り始めてからおよそ30分。
展望台に到着。
展望台
▲つづら尾展望台と思わしき場所。
写真に写っているのは駐車場のごく一部で、
実際にはかなりのバイクと車が止まっています。
というか、バイクと車しかいません。
明らかに私の自転車が浮いています。
思えばこの道って自転車で通るような道だったんでしょうか。
ここまでは非常に沢山の自転車を見てきたはずなのに、
この上り坂に入ってから一台も見ていません。
どう考えても自転車なら避けるべき道だったんじゃ……
       /      \
      /ノ  \   u. \   今になって考えても仕方がないし、
    / (●)  (●)    \  とりあえず、頑張った自分へのご褒美として
    |   (__人__)    u.   |  スイーツ(アイス:105円)でも食べるお
     \ u.` ⌒´      /

帰ってから調べてみたところ、
「琵琶湖一周をするなら奥琵琶湖パークウェイは避けた方が無難。」とか
「相当な根性と体力が必要。」
とか書かれていました。
303号線を通れば楽できたのね orz
(奥琵琶湖パークウェイの地図)

ここで、やる夫は一つの思い込みをしていた。
『「展望台」と名の付く場所は一番高い場所で、
それ以上登り道はない』
という思い込みを……
       ____
     /      \
   /  _ノ  ヽ、_  \   また登り道だお!
  / o゚((●)) ((●))゚o \  あとは下りだけとか思ってたせいで
  |     (__人__)    |  精神的にかなりのダメージを受けたお……
  \     ` ⌒´     / 
再び気合と根性にすがることに。
さすがに登り道がずっと続くようなことはなく、
のぼりと下りが混じった道が続き、最後は下りが続いたため、
結構なスピードで駆け下りていきました。
[午前11:30]
       ____
     /⌒  ⌒\
   /( ●)  (●)\     平坦な道に復帰したお!
  /::::::⌒(__人__)⌒::::: \   あたりには自転車のひとも沢山いて安心だお
  |     |r┬-|     |   (さっきまでの道はバイクと車ばっかしとおってたお)
  \      `ー’´     /
しばらく進んでいると、分かれ道から、
マウンテンバイクの集団がやってくるのが見えました。
        ____
       /      \!??
      /  u   ノ  \     今、見えたのって8時ごろに争った集団じゃ……
    /      u (●)  \    まさか子どもも多いのにあの坂を登って……
    |         (__人__)|   いや、さすがにそれはなさそうだお。
     \    u   .` ⌒/    となると迂回して楽に行くルートがあったということに……
           ____
       /::::::::::::::::\
      /::::::─三三─\
    /:::::::: ( ○)三(○)\  
    |::::::::::::::::::::(__人__)::::  | 悲惨なことが頭をよぎったけど気にせず進むお!
     \:::::::::   |r┬-|   ,/  マウンテンバイクの集団なんて沢山いるから
    ノ::::::::::::  `ー’´   \  きっと似てるだけで別の集団だったに違いないお!
  /:::::::::::::::::::::            
 |::::::::::::::::: l   
[午後1:30]
奥琵琶湖パークウェイを除くと、8時ごろから順調に時速20kmを出し続けていましたが、
唐橋まで残り50km程となったここに来て足に異変が……
           ____
       /      \
      /ノ  \   u. \   足がめちゃくちゃ重くなってきたお……
    / (●)  (●)    \  今のペースを維持するのは無理かもしれないお……
    |   (__人__)    u.   |  
     \ u.` ⌒´      /
午後4:00に唐橋到着を予定したんですが、
泣く泣くペースを落とし時速15km程に。
これで唐橋到着は午後5:20分ほどに。
そこからは足が痛いのをひたすらに堪えながら、
必死にペースを落とさないように頑張るだけでした。
ちなみに気温は30度。死ぬ……
そうしているうちに悲惨なことに気づきました。
     ____     
   /      \     
  /  ─    ─\    琵琶湖が……
/    (○)  (○) \   
|       (__人__)    |   消えた…… 
/     ∩ノ ⊃  /     
(  \ / _ノ |  |     
.\ ”  /__|  |  
  \ /___ /
今回は琵琶湖を時計回りで回っていたので、
右手側には常に琵琶湖が見えるはずでした。
しかし、気づくと右にはなんと山が……
道を間違えたとしても逆戻りする元気なんてもうありません。
とりあえずあってると信じてひたすら直進しました。
すると、コンビニを発見。そこで休んでいた二人組みに突撃。
      ____
     /⌒  ⌒\
   /( >)  (<)\     琵琶湖に行きたいんだけど、
  /::::::⌒(__人__)⌒::::: \    どっちに行けばいいお?
  |    /| | | | |     |    
  \  (、`ー―’´,    /   
        _,. -‐===r‐- 、
       _, ‐’´ ,r’´三三ミ/==、、\
   ,. -‘”  ,  / イ´r-、!’⌒’,  ヽ ヽ
 /イ  / / /  ! |ミ、Y´’, ’,ヽ ヽ ‘,
/’´/ //  i | !   ! i``”´^’, ! ‘,  ‘, i
‘ / /// i ! ! !! ‘, ! ‘,    __!,,|__!   !|
 | ,イ, ! !  ! | |’, !’, ヾ、ヽ /__ !| ! !   !! 
 |/| ! | |  ‘,TTヽ、’,ヾヾ`ヽ’´ o`゙ レ  ,!|  
  !|! i ‘、 ‘, ヾr’´o`     ‐–‘ ノ’⌒リリ   多分むこうのほうじゃないっスか?
  l| ‘,’,、ヽヽ ヽー” ’  _     rノノ   
    ヾ ヽ`ヾ、ゝ ヾ二– }   ノァイ
           丶、 ` ̄´´ ,. '”!’ ´
              ,..>r ‘”   ,lヽ
            _ノ ヾ __,.. -‘”  ‘,ヽ、
        _,. -‐i  ,イ`} i i”i     ,.ゝ、
  ,. -‐”´   |/ Y 丿/ !   /    丶
           ____
       /::::::::::::::::\
      /::::::─三三─\
    /:::::::: ( ○)三(○)\  
    |::::::::::::::::::::(__人__)::::  | 山の方を指されたお!
     \:::::::::   |r┬-|   ,/  まさかこれは山登りフラグ?
    ノ::::::::::::  `ー’´   \  
  /:::::::::::::::::::::            
 |::::::::::::::::: l   
          ,. :::´:::::;::::/:::::::::::::::::::::::`丶、
         /;::::::::/:::/:::::::::::::::::、:::::::::::::::::\
         /ァ´:::::::::::::::/::::::::::::::::::::::\:::::::::::::::::ヽ
       /’ /:::::::::/::::::/::::::::::::::::、::::::::::::\::::::::::::::ハ
         /::/::::/::::::/::/:::::::i::::::::ヽ:::ヽ:::::::ヽ::::::::::::::’
      /::/::::/::::::/:/!|::::::::|::|::::::::’::::::’:::::::::ヽ:::::::::::::l
       l:::|::::::|:l:::::l/\!:::::::|::|、:::::::!::::::l::::::::::l:::::::::::::|
       レ’|::::∧!::::トf卞ヽ::::|リ‐ヽ:::|:、:::|\:::::l:::::::::::/
       |::/ V:::l ゞ’  \! T仡フ7ヾ ヽ::|ヽ::::/
       |/  \l  /     ` ´    ,. リ//  このまま直進したら
              ヽ             〃//    琵琶湖大橋にはいけるんだが……
              ヽ ‐-     //:::/      
              ヽ    ..  ´  l-〈
           __,.ィ’´ 八´    /   !\
      ,. ’  ̄    /   !  \_∠     |  ト、 ̄   ‐-   _
     ,イ       /   |  /  ̄`’,    |  l \      iヽ
     / |      /   | ハ:.:.:.:.:.∧  /|   ,        l ’
    ,′l      /    |V }=:.:./ ∧/ .l   ヽ         !  i
    i  l      /    |  /:.:.:.:V   l   ハ     i /  l
    /!  ヽ  i  /      ! l:.:.:.:.:.:l   ,′    !    l /   l
   {  ヽ  ‘ l. /      | !.:.:.:.:.:.:!  /     |    l’     |
         ____
        /\  /\
      /( ●)  (●)\
     / :::::⌒(__人__)⌒:::::\ 
     |     |r┬-|       | 
     \     ` ー’´     /
     /          \
      | ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ |  トン
   _(,,) 命拾いしたお   (,,)_
  /  |              .|  \
/    |               .|    \
    .|__________|
琵琶湖が見えないものの最終的には合流できるので問題ないようです。
そこからしばらくすると無事琵琶湖が見えてきました。
本当によかった。
[午後3:30]
市街地に到着。
そして、そこで見たものは……
琵琶湖大橋東詰め
▲琵琶湖大橋東詰め。自転車は無料っぽいです。
琵琶湖大橋との実に9時間40分ぶりの再開でした。
少し元気を取り戻し再び自転車をこぎ始めました。
[午後5:10]
               __,/__/⊥…–‐=’ -‘ー─— 、._
       ,.ィニニ.ヽ_,/ – ‘´ - 、         ̄ ̄- 、 ̄``ヽ
   ,. -‐←─—くァ’´/, ’´ ,. –、           `ヽ、
  〈:.:.:.:.:.:.ヽ ̄,. ‐’7   /   //- ヽヽ  ヽヽ ヽ ヽ ヽ \ ヽ.
  ヽ:.:.:.:.:.:.V:::::::/   / / // l  ! i   i ヽヽ ヽ ヽ ヽ.ヽヽ.ヽ
.  / ヽ:.:.:.:.:.:ヽ:イ ,ィ′   i::i:l l: lji :トi  lLl__:}i .:}}、 .:}、.:::i. l i }
  l / 〉.:.:.:.:.:.N`<:::l:    l::/l,ム‐7 l l |:: il l i: l`Tトl、:l l l ト、: |   |' /7   l ト、::`!:   ,レ'7' j::/- リ ! リ j lリ,ュj ハ:|l:l:l !l l:|   l i l    l 〉:ヽ|::   i | _,.ィテラ/  レ′ ノ1ノiトj | lリ リ ,リ     . l l └ ┬--iハ::l:::   i l7トッ:チi|        トッi| l |  l  !: l::::/ :: l:.:.:.:゙l::::   .い い:::_,! ....::::::: , └-' l l  もう...ゴールしてもいいよね。  | l:: l:/    l:.:.:.:.:l::::. . い `¨´:::::     ー' ::::: ノ ハ  l l::./    l.:.:.:.:.:l:::::. ヽ ヽヽ       ´  /  い. . l l└- ..__l.:.:.:.:.:.:':::::.:..ヽ. `弋 - ..____, イ:::::  :い、 .  い::::::.::::::::レ_.:.:.:.:.:.:l、::::::.. ヽ. \____|┐   l::::::.   ::い.   ヽヽ.:.:::.::::::::i丁丁´ ヽ:::::::::...::::....`ヽ、.ヽ   ヽ::::.. .:::iい.    ト、ヽ.:::::::::::l:l::::| /,> 、:::::::::::::::::.... `ヽ.   ヽ::::.. ::i. '.    lj ヽ. .:.::::::::il::::|〈ィ´,ィ´ ̄` ー- 、_:::..:. ヽ   ヽ::. :::l  l .   /  :ヽ.:.::::::::l::::l l7//        `ヽ:::. '.   i:::..::l: |   /   .::} .::::::::l:::l |//              ヽ: }   |::.:::l: l 唐橋
▲ゴール(唐橋)
琵琶湖一周の基点唐橋です。
実際はここからスタートしたわけじゃないんですが、
そんなこはもうどうでもいいです。
とにかくゴールはゴールです。

PrologのバックトラックとGUI

5月 3rd, 2008

XPCEを使えばPrologで自由自在にGUIが使えるんですが、
そうすると、どうもプログラムがPrologっぽくなりません。
というのも、画面の表示を書き換えたり、
さらには変数の値を書き換えたりするので、
バックトラックを極力避けるような作りになるためです。
GUIとバックトラックをどうにか共存できないかと考えたところ、
マルチスレッドにする方法を思いつきました。

  • 一つ目のスレッドがGUIを用いた入出力などを管理する。
  • 二つ目のスレッドは通常のPrologのプログラムを走らせる。
  • 二つのスレッドはメッセージ通信を行う。

この考えでどうにかならないかと思い試してみました。
XPCE
走らせたプログラムはこんな感じです。

test :-
(test1 ; thread_send_message(main, [println, 'No'])).
test1 :-
thread_self(S),
thread_send_message(main, [println, 'member(X, [1,2,3,4,5])']),
member(X, [1,2,3,4,5]),
concat_atom(['X=', X], Text),
thread_send_message(main, [println, Text]),
thread_send_message(main, [click_wait, S]),
check,
thread_send_message(main, [println, 'Yes']).
check :-
thread_get_message(Msg), !,
Msg == right.

member(X, [1,2,3,4])を行い、Xが適当な値に単一化されると
それを表示し(別のスレッドに アトムprintlnと共にthread_send_messageで送信しています)、
画面がクリックされるのを待ちます
(アトムclick_waitと自分のスレッドIDを送信すると、
画面がクリックされたときにアトムleftかrightが送信されるので、
それをthread_get_messageで受け取っています。)。
右クリックされると、画面にYesと表示して終了します。
左クリックされると、バックトラックが起こりmember(X, [1,2,3,4])が再び実行され、
Xが別の値に単一化されます。Xが単一化できなくなると、
画面にNoと表示して終了します。
……GUIとPrologっぽいのプログラムを共存させようと思ったんですが、
これをのPrologっぽいプログラムといっていいのやら。
けどまあ、とりあえず無事動いたので満足です。
もうすこし抽象化すれば見た目がマシになるかも。

XPCEのbitmapクラス

5月 1st, 2008

PrologのXPCEで遊んだときのメモ。
画像ファイルの読み込みは物凄く簡単。

new(BM, bitmap('hoge.bmp')).  % hoge.bmpを読み込む

しかし、このようにして作ったbitmapオブジェクトはread-onlyとなり、
invert, xor, orといった破壊的なメソッドを呼び出すことが出来ない。
これを解決するには、コピーを作ってそっちを操作すればいい。

get(BM, copy, CopyBM).
send(CopyBM, invert)  % 色を反転させる