知恵袋の「うそつき問題」をRubyで解いてみました。(^_^;
というより、拙ブログのPythonプログラムから翻訳してみました。(^_^;
論理包含 Imp と論理等価 Eqv をメソッドにしてみました。(^_^;
A~Eの5人で論争した結果、次のような、A、B、Cの発言があった。
A「Bはウソをついている」
B「Eはウソをついている」
C「Dはウソをついている」
以上の事ことから判断して確実にいえるのは、次のうちのどれか。
1 ウソつきは3人いる。
2 正直者は3人いる。
3 Bがウソつきであるとき、Dもウソつきである。
4 Eがウソつきであれば、ウソつきはもう2人いる。
5 Aが正直者ならば、Dも正直者である。
● Liar1.rb
# encoding: Shift_JIS # Liar1.rb # 論理包含「P⇒Q」の真理値を得る関数 imp def imp(p,q) return (!p)||q end # impのメソッド版 Imp def true .Imp q; imp(true ,q) end def false.Imp q; imp(false,q) end # 論理等価 eqv def eqv(p,q) return !(p^q) end # eqvのメソッド版 Eqv def true .Eqv q; eqv(true ,q) end def false.Eqv q; eqv(false,q) end # 真理値表の1行を文字列で得る def getRowOfTruthTable(lst) result = '' for b in lst result += (b ? ' T' : ' F') end return result end # 確実にいえる選択肢を1つ得る def getAns(cho) puts 'Error!' if cho.count(true)!=1 ar = [] for n in 1..cho.size ar.push(n.to_s) if cho[n-1] end return ar.join(',') end def main() tm = Time.now # Timer Start tf = [true, false] choices = [true]*5 puts ' A B C D E 1 2 3 4 5' tf.product(tf,tf,tf,tf).each do |p| a,b,c,d,e = p next if !((a).Eqv(!b)) # 条件A next if !((b).Eqv(!e)) # 条件B next if !((c).Eqv(!d)) # 条件C # チェックを潜り抜けたものを表示 t1 = getRowOfTruthTable(p) # 選択肢のチェック choices[0] &= (c1 = (p.count(false)==3)) choices[1] &= (c2 = (p.count(true )==3)) choices[2] &= (c3 = ((!b).Imp(!d))) choices[3] &= (c4 = ((!e).Imp(p.count(false)==1+2))) choices[4] &= (c5 = (( a).Imp( d))) t2 = getRowOfTruthTable([c1,c2,c3,c4,c5]) puts '%s %s'%[t1,t2] end puts '∴%s'%getAns(choices) print "Runtime : %.3f [sec]\n"%(Time.now-tm) # Timer Stop & Disp end if $0 == __FILE__ main() end
●実行結果
A B C D E 1 2 3 4 5 T F T F T F T T T F T F F T T F T F T T F T T F F T F T T T F T F T F T F T T T ∴4 Runtime : 0.000 [sec]
※参考URL
●知恵袋の「ウソつき問題」をPythonで解いてみた。(5) - rscのブログ
●【論理包含演算子Imp】の質問 - rscのブログ