代码之家  ›  专栏  ›  技术社区  ›  PassionateDeveloper

collections.shuffle适合扑克算法吗?

  •  4
  • PassionateDeveloper  · 技术社区  · 15 年前

    在Java中有一个扑克系统,它使用 Collections.shuffle() 在发牌之前,在所有可用的牌上。

    所以收集了52张2-9,J,Q,K,A四种类型的卡片。

    之后我们 集合。随机播放() .

    问题是,似乎(直到现在我们还没有大的统计数据,可能我们只看到很多统计推断),算法是非常不干净的。

    所以,是 集合。随机播放() 对扑克算法好吗?


    评论答案: “不干净”的意思是有时非常神秘。很多用户抱怨“它与Live/Other Pokerrooms不同”。 我用这个系统玩了很多,必须说,我同意,我在2000岁以下的人中看到了3个皇家闪光,在这个系统中我看到了手,在其他口袋里我看到了超过10万只手,直到今天我看到了2只手。

    7 回复  |  直到 12 年前
        1
  •  9
  •   Hank Gay    15 年前

    如果这是一个严肃的扑克应用程序,在那里钱可以换手,简短的答案是不。对于这样的事情,你应该真的使用一个真正随机性的硬件来源。

    稍微长一点的答案是:如果你不能得到硬件来实现真正的随机性, Collections.shuffle(List, Random) 可以 如果你提供一个 SecureRandom . 这个解决方案的难点在于找到一个好的种子值。

    更新:基于您的澄清,我建议您研究一下如何播种PRNG(假设您已经在使用密码安全的实现;如果没有,请先这样做)。你应该 使用有限的种子。其他需要考虑的事项:

    • 您可能应该为每个游戏实例化一个prng
    • 你应该只在双手之间移动甲板;从你的问题来看,不完全清楚你也没有在翻滚、转弯、河流等之间移动甲板。
        2
  •  6
  •   Jack    15 年前

    这个 Collection.shuffle 使用的O(N)实现 Fisher-Yates洗牌算法 .

    随机索引是用Java的正常PRNG选择的,所以它将是近似均匀的:每一个甲板的洗牌都将是尽可能多的每一个。

    这对于你想做的事情来说是很好的,但是当你想要真正的随机化时,你应该引入一些真正的随机因素(比如 System.currentTimeMillis() 用于种子随机数发生器)或更可实现的东西,如专门的硬件。

        3
  •  4
  •   Jonas B    15 年前

    好吧,我通常不喜欢别人这样对我说,但是是的和不是的。这和pickrandomcardbetween(152)差不多,在随机性方面使用rand()函数。

    没有一点是,对于任何处理机会或随机值的东西,你需要合适的硬件,一台普通的计算机甚至不能远程生成任何类型的真正随机结果。

    编辑:如果你的PokerSystem是为了好玩,那是一回事,但是当涉及到钱的时候,人们会因为你创造的随机结果而绞死你。

        4
  •  4
  •   justkevin    15 年前

    我建议阅读这篇文章:

    How We Learned to Cheat at Online Poker

    作者研究了一个软件包,发现了几个缺陷。一个严重的问题是种子。如果从32位种子开始(并且在随机播放期间不生成新的独立种子),则只能生成2^32个不同的随机序列。52张牌组有2^226次可能的洗牌,这意味着只会产生一小部分可能的牌组订单。

    一个玩家知道5个扑克牌位置(奥马哈7个)。如果玩家知道洗牌算法,他可以根据所看到的牌猜出候选种子是什么。这给了他一个很大的优势,在推断什么是隐藏的卡的概率。

        5
  •  2
  •   Community Mohan Dere    8 年前

    如果这是一款涉及金钱的严肃的扑克软件,那么答案将是否定的(对此,你需要一些真正随机性的来源)。但是,对于简单的情况,它和其他算法一样是一个很好的解决方案。

    如果您需要有关随机播放算法本身的更多信息,请参见 Java's Collections.shuffle is doing what? .

        6
  •  0
  •   Beothorn    15 年前

    问题是随机产生的数字在统计上是随机的。这意味着洗牌不像一副牌,因为它比现实生活中的洗牌更随机。要想得到更真实的东西,你需要模拟现实生活中洗牌的方式,比如你剪了多少次牌等等。我看到了一个网站,上面有一张图表,比较了一个真正骰子的结果和计算机生成的结果,显示结果有多不同。计算机的结果分布比较均匀,但我似乎在谷歌上找不到链接。

        7
  •  0
  •   Jonas Bergström    12 年前

    我可以告诉你,这不是大型扑克网站的做法。 预先洗牌使牌组在游戏服务器的某个地方的内存中可用,也就是说,如果您有权访问服务器主机(如ops),就可以读取它。 相反,只要需要,卡就从卡组中随机抽取(在硬件RNG上使用安全随机)。当你收到“错误”的社区卡时,这有时会让你头脑混乱,因为如果你只是等了一毫秒再打电话,他们就不一样了:)