#前書き
モンティホール問題というのをこないだ知ったので,実際にプログラムで解いてみた.
#Monty hole problem
確率に関する問題,例題は以下の通り
- プレイヤーの前には3枚の扉があり一枚にはアタリである車が,残り二枚にはハズレであるヤギがいる.
- プレイヤーは一つ扉を選ぶ.
- すると出題者がプレイヤーが選んでいない二枚の扉の中からハズレの扉を一枚開いて見せる.
- 最後にプレイヤーはそれを見てから,先ほど選んだ扉をもう一枚の扉に変えるかどうか決めることができる.
この問題では最後に二枚から一枚を選んでいるため一見当たる確率が50%に見えるが,実は選択する扉を変えると当たる確率が66%になる.
以下C言語による実装
monty.c
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#define coc 1 //選択を変えるか否か
void main(){
int car, choise, sheep;
int cnt=0, num=10000;
srand((unsigned)time(NULL));
for(int i=0; i<num; i++){
car = rand()%3; //当たりを決める,ドアは0,1,2の三枚
choise = rand()%3; //一回目の選択する
if (choise != car) sheep = ((car+1) ^ (choise+1)) -1; //選択がハズレなら出題者が見せるハズレの扉は自ずと決まる(排他的論理和)
else if((rand()%2+1)==1) sheep = (car+1)%3; //1/2の確率でchoiseの一つ次か一つ前かが決まる
else sheep = (car+2)%3;
if(coc==1){ //選択を変える場合なら一回目の選択とハズレの排他的論理和を取る
choise = ((sheep+1) ^ (choise+1)) -1;
}
if(choise == car){ //統計
cnt++;
}
}
printf("当たった確率:%.1f%%", (double)cnt/num*100);
}
正直簡単だが,個人的に面白かったのは
すでに二つの扉の値が与えられており,あと一つの扉の値が欲しい場合にXORを使うところ.
もちろん高級なライブラリとかを使えばこうしなくても良いのだろうが...