本を読む

読書やコンピュータなどに関するメモ

1つの条件で複数の変数を束縛する方法を考える

 Schemeコードバトンでいじった箇所のうち、気になっていた部分について、ひげぽんさんからチェックをいただきました。

swap! って何だと思ったらマクロだった。こういう使い方は自分はしないから面白いなー。

 はい、苦しまぎれの使いかたです(笑)。バトンを渡したあともちょこっと考えていたので、問題(と私が思っている)点を、素人なりにまとめてみます。もっとうまいやりかたがありそうなので、ハッカーさんアドバイスpls。

書いたコードと考えたこと

 もともとのプログラムは、英単語を出題して日本語の意味を考えさせるものです。私のところに来たときには、リスト構造のデータから問題と回答をとりだすアクセッサ手続きが、それぞれ整備されていました。

(word-spec-word spec)
(word-spec-meaning spec)

 で、私は、逆に日本語を出題して英単語を考えさせるオプションを追加してみました。まず考えたのが、アクセスするときに条件判断する方法です。

(if ($$ reverse) (word-spec-meaning spec) (word-spec-word spec))
(if ($$ reverse) (word-spec-word spec) (word-spec-meaning spec))

 あるいは。

((if ($$ reverse) word-spec-meaning word-spec-word) spec)
((if ($$ reverse) word-spec-word word-spec-meaning) spec)

 これで駄目なわけじゃないのですが、同じ条件判断を2箇所でやっていて、しかも両者が排他的な関係にあるのが、自分には気持ち悪く感じました。…手続き脳ですいません。

 となると1つの条件でset!するかな、と考えたわけです。

(let (question answer)
  (if ($$ reverse)
      (begin
        (set! question word-spec-meaning)
        (set! answer word-spec-word) )
      (begin
        (set! question word-spec-word)
        (set! answer word-spec-meaning) ))
   … )

 さすがにこれは逆に、Scheme的に気持ち悪い。というわけで、swap!マクロを定義して、気持ち悪さを軽減してみました。

(let ((question word-spec-word)
      (answer word-spec-meaning) )
  (when ($$ reverse)
      (swap! question answer) )
  … )

 let直下にswap!を起くことで状態臭を減らしたつもりではありますが、いずれにしてもSchemeっぽくないなあと。これがバトンを回したバージョンです。

多値で?

 提出した後でもちょっと考えてました。で、問題をこのエントリーのタイトルのように「1つの条件で複数の変数を束縛する」と自然言語で考えてみたところ、「多値」という方法を思いつきました。

(import (srfi :8))
(receive (question answer)
         (if ($$ reverse)
             (values word-spec-meaning word-spec-word)
             (values word-spec-word word-spec-meaning) )
         … )

 これがキレイな方法かどうかはともかく、問題に行き詰まったら異なる抽象形式に変えて考えてみる(プログラミング言語→自然言語とか)のも一つの手かな、と。

コメント

コメントの投稿

管理者にだけ表示を許可する

トラックバック

http://emasaka.blog65.fc2.com/tb.php/702-50787af5

 | HOME | 

Categories

Recent Entries

Recent Comments

Recent Trackbacks

Appendix

emasaka

emasaka

フリーター。
連絡先はこのへん

Monthly


FC2Ad