用蒙特卡罗方法解决 Monty Hall problem (三门问题)

昨晚(今早?)睡不着觉,就开始想下学期要学的概率论的那些事了,想着想着就想到了著名的山羊与汽车的问题

大意是这样,某电视节目里有这样的场景:三个门后面随机地放有两只山羊和一辆汽车。参赛者可以随机选出一扇门(当然目标是汽车不是山羊);当选手做出选择后,知道车具体在哪扇门后的主持人打开一扇后面有山羊的门。这是选手可以选择更换自己的选择或者不换。问题是,做出哪一个选择后更容易的到汽车呢?

大多数人都会这样思考问题:在主持人打开有山羊的门之前,选手拿到汽车的概率为1/3;而主持人排除一个错误选项后;相当于在两个里面随机抽一个,概率也就变成1/2了,因此换与不换的概率是一样的;都是1/2。昨晚我大概就是这么想的,但又知道答案是换比不换好,因而纠结了好久……

接下来我们试着编个程序来模拟下这个过程:

#include <stdio.h>
#include <math.h>
#include <time.h>
#include <stdlib.h>
#include <iostream>

using namespace std;

int main() {
  int car,choice,change,no_change,open;
  change=0;no_change=0;
  int a[3],goat[2];
  srand(time(NULL));
  cout << "#tchoicetcartopentchangetno_changen";

  for (int t=0;t<500;t++){
    for (int i=0;i<3;i++) a[i]=0;
    choice = rand()%3;
    car = rand()%3;

    a[car] = 1;
    goat[0] = (car+1)%3;
    goat[1] = (car+2)%3;

    if (choice == car){
      open = goat[rand()%2];
      cout << t << "t" << choice+1 << "t" << car+1 << "t" << open+1 << "tt*n";
      no_change++;
    }
    else{ // choice <> car
      if (choice == goat[0]) open = goat[1];
      else open = goat[0];
      cout << t << "t" << choice+1 << "t" << car+1 << "t" << open+1 << "t*n";
      change++;
    }
  }

  cout << "============================n" << "Sum: n" << "Change: " << change << "nNo_change: " << no_change << "n";
}

我设置的模拟次数是500,结果表示,换选项成功345次,不换成功155次。具体结果参见下面链接。

接着做两个解释:

1. 正确答案是什么

其实透过代码我们也可以知道这里应该分为两种情况讨论:

  • 如果我们第一次就选中了汽车(这里的概率是 1/3),那么主持人会随机从两只山羊里选出一只。这是显然如果换了就错过汽车了,应该不换;
  • 如果我们第一次选择山羊(这个概率为2/3),那么主持人一定会打开另一删后面有山羊的门;这是剩下最后一扇门后面就一定是汽车。这时更换选项就会成功。

因此,更换是否成功完全在于第一次是否选错,那么概率也就是 2/3。

2. 为什么 1/2 是错误的

这里我们可以再回到上面看一下那个通俗的错误解释。“主持人排除一个错误选项后;相当于在两个里面随机抽一个,概率也就变成 1/2 了” 而实际上,这里显然选手没有再次做随机选择的能力,而只是选择“换”或者是“不换”。比如说,如果参赛者知道答案,它第一次一定能选中汽车的话,那么第二次机会即使看起来是“在两个里面随机抽一个”,不换的概率就是1;而不是1/2。可以说,这个错误的解释里混淆了概率与结果。


如果还是很难理解的话,可以把问题抽象成小球并扩展到 5 (n) 个。假设有 4 个白球 1 个黑球,当随机抽出一个后,确定地拿出 3 (n-2) 个白球。那么剩下的那个没被拿走的球是黑球的概率不就是第一次抽到白球的概率,也就是 4/5 (1-1/n)了。

这个问题也有人叫做玛丽莲问题,因为这个问题是因为世界上智商最高的人玛丽莲给出了违反直觉的正确解答后才引起广泛的讨论的。这里是她的网站上记录的讨论,可以看到无数的 PhD 倒在的这里……

必要的年终总结日志

欢迎吐槽

一年又过去了,本来这篇日志应该在三星期前就写完了,但一直拖着没写。不过当真正想写的时候,却又发现要写的太多,反而不知道从哪里开始写起了。我一直坚信经历比结果重要,而这一年真的经历了好多,真的很感谢学生会,乐团、乐队的民那和在我身边的所有人。

学术:

不想说太多,因为今年课余生活实在太丰富,倒是这两学期完全没挂科的结果让我很惊讶。随着这两学期学完,文科的东西越来越少,本应该静下心来好好学一学,但最后发现这不过是自己的YY。看了一下下学期的数电教材(感觉比模电不知道高到哪里去了),发现里面的很多东西就是我高考后想看的,果然自己想过的东西前人都做好了。而之前想做成创新实验项目的一个3D眼镜也有人做了(http://audio.pconline.com.cn/mp4/review/1111/2587383.html),另一个wiki虽然有点头绪,但很明显是做不下去的,真想套现的话可能还是移动开发比较好。最后感觉还是专心研究模式识别吧,我们专业估计就指望这个活呢,数模什么的虽然可能用不上,但还是找个理由看看神经网络比较好(//不过按照我们数据结构老师的说法,Lisp做的砖家系统没前途……)

Geeky的方面:

这一年这的变成死宅了,原来会的东西现在也不会了,跟Dage和玉帝比我真的弱爆了。院会面试的时候还说过一个学妹很Geeky,到最后却发现自己连说Geeky的资格都快没有了。自《三体三》之后我就几乎没再看过什么科幻作品,好多挂着科幻名号的作品也不过是借着科幻的背景而已。不过抛开科幻因素这些作品也确实不错,比如Level-E和境界线。CS方面只是把C学会了,写了个php+MySQL的投票系统还有学长帮忙,正是因为此才有了网络部的福利。网站也快一年了,里面却什么都没有,可惜总写杂文也没人看啊。话说回来,归根结底还是自己整天不干正经事,很多时间浪费在SNS上,说真的期中考试之后不用i5700了上课效率高了好多。。。

ACGMN:

想说的有好多,但又怕占太多地方。。。总的来说,我恰好是从去年这个时候还是追季番,一周一集,看的是宽叔成名作FRACTALE(然后就发现被所谓的科幻背景坑了)。接着就是三月份开始加了乐队,这时我的三次元生活也开始丰富了起来。在乐队不小心(?)cos了两回伪娘,黑历史什么的连自己都找不到了。接着就是5月份去漫展见到了 @AstroProfundis,8月份在沈阳的漫展见到了中岛爱唱了四五首歌,买了三本轻小说(然后前天才读完第一本《神様のメモ帳》……)。9月的AM3个人感觉相当成功,在麻雀瓦舍感觉人生都变得完整了。

就整个这一年看过的番組来说,石头门是给我印象最深的(可惜游戏还没汉化),看起来小圆这种风格的作品是趋势啊;音乐方面则恰好是一年前的除夕那天看了B站上的《xxx神曲xxx》开始接触各种ACG Music,也有很多因为觉得OP/ED/插曲好听才开始看的动画;游戏除了为了看FZ把FSN玩了之外没啥其他收获;漫画则是前两天期末考试前把《未来日記》看了。ACGMN全了

epilogue:

“一年好快啊~”,但这一年所发生的事和所认识的人真的比想象的要多好多。记得去年第一天写日志的时候用了一番の宝物和Brave Song的歌词,这次却完全找不到能形容我现在心情的曲子……用glassware这个钢琴曲吧,现在的心情其实很平静,但也有人说这曲子很悲伤。。。

←不要吐槽这个的大小就行。。。

PS:本来以为假期没事干,闲的时候能练练鼓,最后也找到玩的了。这假期真充实啊,平均两天自己出一次门……

PS2:某些人真不咋地