Hatena::Groupcadr

わだばLisperになる このページをアンテナに追加 RSSフィード

2004 | 12 |
2005 | 01 | 02 | 07 | 10 | 11 |
2006 | 06 | 07 | 08 | 09 | 10 | 11 | 12 |
2007 | 01 | 02 | 03 | 04 | 05 | 06 | 07 | 08 | 09 | 10 | 11 | 12 |
2008 | 01 | 02 | 03 | 04 | 05 | 06 | 07 | 08 | 09 | 10 | 11 | 12 |
2009 | 01 | 02 | 03 | 04 | 05 | 06 | 07 | 08 | 09 | 10 | 11 | 12 |
2010 | 01 | 02 | 03 | 04 | 05 | 06 | 07 | 08 | 09 | 10 | 11 | 12 |
2011 | 01 | 02 | 03 | 04 | 05 | 06 | 07 | 11 |

2009-08-17

Algolの引数の名前渡し

| 00:40 | Algolの引数の名前渡し - わだばLisperになる を含むブックマーク はてなブックマーク - Algolの引数の名前渡し - わだばLisperになる

引数 - Wikipedia

を眺めていて、Algolの引数の名前渡しが面白いなと思ったので、マクロで書くとどんな感じになるのか試してみることにしました。

swap(x,y) {
 tmp = x;
 x = y;
 y = tmp;
}
この例に対し、x=i, y=a[i]という"式"を渡すとする。仮にi=2だったとすると、
tmp = x;
    x=i=2 なのでtmpは2になる。
x = y;
    xはiを渡されているのでiがyの値になる。yはa[i]だから、iはaの2番目の値になる。
y = tmp;
    yはaのi番目の値だが、前手順によりiはa[2]になっている。従ってy=a[a[2]]になる。
このような複雑さもあって、ALGOL以外で名前渡しが採用された事例はほとんどない。

というような解説が載っているのですが、マクロで書くと、

(defmacro swap (x y)
  (let ((tmp (gensym)))
    `(let (,tmp)
       (setf ,tmp ,x)
       (setf ,x ,y)
       (setf ,y ,tmp))))

こんな感じになるのでしょうか?

y=a[i]という式を渡すというのがどう解釈されるのか分からないのですが、とりあえず、setf的にしてみました。

(let ((i 2)
      (x (list 1 2 3 4)))
 (swap i (elt x i))
  x)
;=> (1 2 3 2)

マクロ展開

(LET ((I 2) (X (LIST 1 2 3 4)))
  (LET (#:G2488)
    (SETQ #:G2488 I)
    (SETQ I (ELT X I))
    (SB-KERNEL:%SETELT X I #:G2488))    
  X)
;=> (1 2 3 2)

なにか解釈を間違えてる気がしてならないですが、実際にこういう動作だったとすると、随分複雑ですねー('-'*)

それとも、この例が複雑なのかな?…

(let ((x 10)
      (y 20))
  (swap x y)
  (list x y))
;=> (20 10)

…こういう使い方を想定しているとすると、解説の例が複雑すぎるのかもしれませんね(笑)

ゲスト



トラックバック - http://cadr.g.hatena.ne.jp/g000001/20090817