我知道python提供随机模块来做一些简单的抽奖。假设random.shuffle()是一个很好的。
但是,我想建立自己的简单。我该怎么看?乐透背后是否有任何具体的数学哲学?
让我们说,最简单的情况。 100个名字并随机生成20个名字。
我不想使用shuffle,因为我想学习自己构建一个。
我需要一些建议才能开始。感谢。
答案 0 :(得分:4)
你可以生成自己的伪随机数 - 背后有大量的理论,例如here - 当然你将无法与Python的{{1}竞争“Mersenne twister”(在我指向你的大维基百科页面的中间解释),质量或速度,但为了理解,这是一个很好的努力。或者,您可以获取物理随机数,例如Linux机器上的random
或/dev/random
(Windows机器也有自己的接口) - 一个具有更强的物理随机性,另一个一个人有更好的表现。
一旦你拥有(或借用/dev/urandom
;-)伪随机(或真正随机)数字生成器,从100中随机挑选20个项目仍然是一个有趣的问题。虽然shuffling是一种更通用的方法,但是可以更容易理解,假设你的random
函数返回0和N之间的随机或伪随机int:
myrand(N)
绝对不是最大效率,但是,我希望,最大限度地清楚! - )用语言:只要需要和可行,从其余的中选择一个随机项目(辅助列表def pickfromlist(howmany, thelist):
result = []
listcopy = list(thelist)
while listcopy and len(result) < howmany:
i = myrand(len(listcopy))
result.append(listcopy.pop(i))
return result
给我们“剩下的“在任何一步,并由listcopy
修改而不改变输入参数.pop
,因为它是一个浅的副本。”
答案 1 :(得分:3)
请参阅Knuth的Fisher-Yates Shuffle中描述的The Art of Computer Programming。
答案 2 :(得分:2)
我赞美你想要自己做这件事。
早在20世纪50年代,大多数没有超级计算机(当时)的人都无法使用随机数字。兰德公司出版了一本名为一百万个随机数字的书,其中包含100,000个正常偏差,其字面意思是:随机数。它非常棒,因为它使得外行人能够将高质量的随机数用于研究目的。
现在,回到你的问题。
我建议您阅读instructions如何使用书籍(是的,它附带说明)并尝试在Python代码中实现它。这不会有效或优雅,但您将理解您最终解决的算法的含义。我喜欢指导你的部分
将书打开到未经选择的页面 数字表并盲目地选择一个 五位数;这个数字跟 第一个数字减少了模数2 确定起跑线;他们俩 最初的数字 选择的五位数字减少了 以模50来确定起始点 起始行中的列
阅读那个数字表是一门艺术!
可以肯定的是,我不鼓励你为生产代码重新发明轮子。我鼓励你通过实现一个聪明的(如果不是非常有效的)随机数生成器来了解随机性的艺术。
我的工作要求我使用高质量的随机数,在有限的场合我发现网站www.random.org是一个非常好的洞察力和材料来源。来自他们的网站:
RANDOM.ORG提供真正的随机数 互联网上的任何人。该 随机性来自大气 噪音,用于许多目的 优于伪随机数 通常用于计算机的算法 程式。人们使用RANDOM.ORG 拿着图纸,彩票和 抽奖,驾驶游戏和 赌博场所,用于科学研究 应用程序以及艺术和音乐。
现在,去实施自己的彩票。
答案 3 :(得分:1)
您可以使用:random.sample
返回k长度的唯一列表 从人口中选择的元素 序列。用于随机抽样 没有替代。
对于更低级别的方法,在循环中使用`random.choice':
从中返回一个随机元素 非空序列seq。
Python中的伪随机生成器(PRNG)非常好。如果你想更低级别,你可以实现自己的。首先阅读this article。彩票的数学名称是“无需替换的抽样”。谷歌的信息 - 这里是good link。
答案 4 :(得分:0)
基于软件的彩票号码生成方法的主要缺点是软件生成的所有随机数都是伪随机。
这可能不是您的简单应用程序的问题,但您确实询问过“特定的数学哲学”。您会注意到所有商业彩票系统都使用物理方法:带数字的球。
在幕后,物理彩票系统产生的数字将被仔细审查,以表明非随机性和消除它的步骤。
正如我所说,这可能不是您简单应用的考虑因素,但真正的彩票(“特定数学哲学”)的首要要求应该是在数学上可证明的随机性