プリプロセッサの話題は、今日は時間と気力がないので、ちょっとお休み。
今日は、以下のような問題を @IT にあげてみた。
参照 : http://www.atmarkit.co.jp/bbs/phpBB/viewtopic.php?mode=viewtopic&topic=33022&forum=3&start=170
あなたは、「J氏」「R氏」「B氏」の3人が常駐する掲示板に来ました。
しかし、彼らは匿名(便宜上1・2・3とします)と名乗っています。
以下の条件によって、1,2,3の誰が「J氏」「R氏」「B氏」であるのかを特定して下さい。
3人は、お互いが誰なのかを知っています。
1・2・3の何れかの人を指定して、掲示板で質問を投げかけられます。
その質問は必ず「はい」か「いいえ」で答えられるものとします。
掲示板は、あと6回投稿すると書き込めなくなるので、3回しか質問できません。
「J氏」「R氏」「B氏」の3人は、特徴があります。
「J氏」は常に「真」の回答を答えます。
「R氏」は常に「偽」の回答を答えます orz
「B氏」は完全にランダムに「真」か「偽」のどちらかを回答します。
また、3人からは、特有の言語「なっ!」か「ぜ!」と返答されます。
この「なっ!」か「ぜ!」のどちらが「はい」でどちらが「いいえ」かはわかりません。
どのように質問すれば、1・2・3が各誰なのかを特定できますか?
注意!! (軽くヒント)
JとRが同じ回答、つまり「はい」と言うべき質問ができるだろうか?、と考えてみる。
これはプログラマなら次のようなコードに例えてみるのがわかりやすそうだ。
j = (1 + 1 == 2): // j は常に正しい。つまりそのままの結果を受け取る。
r = !(1 + 1 == 2): // r は常に間違う。つまり逆の結果を受け取る。
上記の結果は当然、r = true; j = false; になる。
では、どちらも false, あるいは true になるようにするにはどうすれば良いだろう?
答えは簡単だ。
j = (r == j); // j はそのままの結果を受け取るから、false
r = !(r == r); // r は逆の結果を受け取るから、false
つまり、どちらも false になる。
これを質問になおすと、「あなたはR氏ですね?」となる。(回りくどいか?w)
では、これを踏まえて、ある人が JかRかのみを特定するための質問は作れないだろうか?
j = ((r == j) == true); // j はそのままの結果を受け取るので、false
r = !(!(r == r) == true); // r は逆の結果を受け取るので、true
これを質問になおすと、「あなたはR氏ですね?、と質問されたら「はい」といいますか?」となる。(余計ややこしくしてないか?)
この問いに、「いいえ(false)」と言えばJ氏、「はい(true)」と言えばR氏と言う事になる。
・・・長くなったので続きは気が向いた時にでもw