博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

博饼的概率

Posted on 2011-10-12 01:39  visiblelight  阅读(2632)  评论(0)    收藏  举报

今年参加了三场博饼,忽略一秀二举,分别只博到两个四进和一个三红。相对我的手气来说真是年年都很衰,今年特别衰。

似乎博了二十几年我从来没有博到过六子和状元插金花,也从没从桌上拿走状元。今天决定算一下概率看我离状元到底有多远...

因为奖项没有重叠,并且高的奖项会覆盖掉低的奖项,所以先从高往下计算吧。

现在都是把状元插金花当成最高。六个骰子里有任意四个是四点,其它二个是一点。所以概率是:

(1/6)^4*(1/6)^2*C(6,4) = 0.00032150205761316862

接下来是六子,六个骰子都是同色的,有六种情况。所以概率是:

(1/6)^6*6 = 0.00012860082304526745

然后是五子,有任意五个骰子是同色,同色情况有六种,另一个不同。所以概率是:

(1/6)^5*(5/6)*C(6,1)*6 = 0.0038580246913580236

普通的四红状元,有任意四个骰子是四,其它两个都不是四。当然得再扣掉状元插金花的情况。所以概率是:

(1/6)^4*(5/6)^2*C(6,4) = 0.0080375514403292162

减掉状元插金花的概率,最后是:

0.0080375514403292162 - 0.00032150205761316862 = 0.0077160493827160472

对堂是顺子,一至六的全排列。概率是:

(1/6)^6*6! = 0.015432098765432094

四进,有任意四个骰子是相同的,当然四红状元除外。概率是:

(1/6)^4*(5/6)^2*C(6,4)*5 = 0.040187757201646079

三红,有任意三个骰子是四点。概率是:

(1/6)^3*(5/6)^3*C(6,3) = 0.053583676268861458

二举,有任意二个骰子是四点。概率是:

(1/6)^2*(5/6)^4*C(6,2) = 0.20093878600823045

当然,得再减掉既是二举又是四进的情况:

(1/6)^2*(1/6)^4*C(6,2)*5 = 0.0016075102880658432

最后概率是:

0.20093878600823045 - 0.0016075102880658432 = 0.1993312757201646

最后是一秀的概率,有任意一个骰子是四点。概率是:

(1/6)*(5/6)^5*C(6,1) = 0.40187757201646102

当然,得再扣掉既是一秀又是四进的情况。这个可以这么计算,首先是四个相同点数的骰子(有五种情况),然后另两个骰子有一个是四点,另一个则还有四种点数可以选。

5*(1/6)^4*(1/6)*(4/6)*2*C(6,4) = 0.012860082304526746

每个顺子对堂其实也是一秀。得扣除。

还有既是一秀又是五子的情况,这个的概率是:

(1/6)*(1/6)^5*C(6,1)*5 = 0.00064300411522633723

所以最终的概率是:

0.40187757201646102 - 0.012860082304526746 - 0.015432098765432094 - 0.00064300411522633723 = 0.37294238683127584

总结一下,各个概率分别为:

状元插金花:0.00032150205761316862

六子:        0.00012860082304526745

五子:        0.0038580246913580236

状元:        0.0077160493827160472

对堂:        0.015432098765432094

三红:        0.053583676268861458

四进:        0.040187757201646079

二举:        0.1993312757201646

一秀:        0.37294238683127584

好了,那么算一下什么都没博到的情况吧。由于上面所有的情况都是相斥的,直接用1.0减掉所有的东西:

1.0 - 0.00032150205761316862 - 0.00012860082304526745 - 0.0038580246913580236 - 0.0077160493827160472 - 0.015432098765432094 - 0.053583676268861458 - 0.040187757201646079 - 0.1993312757201646 - 0.37294238683127584 = 0.3064986282578876

补充一下按同安的规矩,对堂应该是分别三个相同点数的骰子。这个明显比顺子要难出得多。

概率应为:

(1/6)^3*(1/6)^3*[C(6,3)/2]*P(6,2) = 0.0064300411522633721

需要注意是C(6,3)之所以还要除以2是因为每个选中的相同点数组合的另一个对称组合都能够排列出重复的骰子。

比如这样,博出的骰子形状是AAABBB,若点数是五和六,则可能是有排列555666和666555。但是AAABBB的另一个对称组合BBBAAA,同样也能够排出666555和555666。

结论是,三红真的比四进容易博得多,同安对堂甚至比四红状元还要难博。当然最难博到的显然还不是状元插金花,而是六子!还有什么都没有博到的机率其实比一秀还还要低...

为了验证正确率,上一段程序测试一把吧,随机一千万个case看看。

#! /usr/bin/python
# -*- coding: utf-8 -*-

import random

def dice():
	return random.randint(1, 6)
	
class Roxes:
	def __init__(self):
		self.reset()
		
	def reset(self):
		self.data = [dice() for i in range(6)]
		
	def show(self):
		print self.data
		
	def kong(self):
		return not (self.yixiu() or self.erji() or self.sanhong() or self.sijin() or self.duitang()\
				or self.zhuangyuan() or self.zhuangyuanjinhua() or self.wuzi() or self.liuzi()) 
				
	def yixiu(self):
		"""
		一秀:有且仅有一个4,且不是四进或者对堂(顺子)或者五子
		"""
		return self.data.count(4) == 1 and not self.sijin() and not self.duitang() and not self.wuzi()

	def erji(self):
		"""
		二举:有且仅有两个4,且不是四进
		"""
		return self.data.count(4) == 2 and not self.sijin()
		
	def sanhong(self):
		"""
		三红:有且仅有三个4
		"""
		return self.data.count(4) == 3
	
	def sijin(self):
		"""
		四进:有四个相同的非4骰子
		"""
		return any([self.data.count(i) == 4 for i in (1,2,3,5,6)])
		
	def duitang(self):
		"""
		对堂:顺子
		"""
		return len(set(self.data)) == 6
		
	def tonganduitang(self):
		"""
		同安对堂:分别有三个相同骰子
		"""
		return len(set(self.data)) == 2 and self.data.count(self.data[0]) == 3
		
	def zhuangyuan(self):
		"""
		普通四红状元:有且仅有四个4,不包括状元插金花
		"""
		return self.data.count(4) == 4 and not self.zhuangyuanjinhua()
		
	def zhuangyuanjinhua(self):
		"""
		状元插金花:四个4和两个1
		"""
		return self.data.count(4) == 4 and self.data.count(1) == 2
		
	def wuzi(self):
		"""
		五子:有五个相同的骰子
		"""
		return any([self.data.count(i) == 5 for i in range(1,7)])
		
	def liuzi(self):
		"""
		六子:有六个相同的骰子
		"""
		return len(set(self.data)) == 1
	
def main():
	roxes = Roxes()
	k = 0
	yx = 0
	ej = 0
	sh = 0
	sj = 0
	dt = 0
	tadt = 0
	zy = 0
	zyjh = 0
	wz = 0
	lz = 0
	count = 10000000
	c = count
	while c > 0 :
		c -= 1
		roxes.reset()
		if roxes.yixiu():
			yx += 1
		elif roxes.erji():
			ej += 1
		elif roxes.sanhong():
			sh += 1
		elif roxes.sijin():
			sj += 1
		elif roxes.duitang():
			dt += 1
		elif roxes.zhuangyuan():
			zy += 1
		elif roxes.zhuangyuanjinhua():
			zyjh += 1
		elif roxes.wuzi():
			wz += 1
		elif roxes.liuzi():
			lz += 1
		else:
			k += 1

		if roxes.tonganduitang():
			tadt += 1
			
	count = float(count)
	print '空', k/count
	print '一秀',yx/count
	print '二举',ej/count
	print '三红',sh/count
	print '四进',sj/count
	print '对堂',dt/count
	print '状元',zy/count
	print '状元插金花',zyjh/count
	print '五子',wz/count
	print '六子',lz/count
	
	print '同安对堂', tadt/count
	
if __name__ == '__main__':
	main()


输出结果如下,看起来貌似差不多:)

空 0.306341
一秀 0.3729235
二举 0.1994153
三红 0.0537068
四进 0.0402244
对堂 0.015397
状元 0.0077119
状元插金花 0.0003175
五子 0.0038347
六子 0.0001279
同安对堂 0.0064391