用于测试扑克牌手牌的算法(4 到顺子)?

标签 algorithm language-agnostic poker

为了好玩,我正在努力编写一个扑克评估库,并希望添加测试一组给定纸牌的平局(开放式、内顺式)的能力。

只是想知道这方面的“最先进”是什么?我试图让我的内存占用合理,所以使用查找表的想法不太合适,但可能是一个必要的邪恶。

我目前的计划是:

  • 从该组中所有卡片的等级中减去最低等级。
  • 查看特定序列,即:0,1,2,3 或 1,2,3,4(对于 OESD)是否是修改后的集合的子集。

我希望在复杂性方面做得更好,因为 7 张卡片或 9 张卡片组会用我的方法让事情停止。

我们将不胜感激任何意见和/或更好的想法。

最佳答案

最快的方法可能是为每个卡片等级分配一个位掩码(例如 deuce=1、three=2、four=4、five=8、six=16、seven=32、eight=64、nine=128、 10=256, jack=512, queen=1024, king=2048, ace=4096), 并将手中所有牌的掩码值或在一起。然后使用一个 8192 元素的查找表来指示这手牌是顺子、开端、顺子还是无意义的(也可以包括各种类型的后门顺子抽牌而不影响执行时间)。

顺便说一句,使用不同的位掩码值,可以快速检测出其他有用的手牌,例如同类两手、同类三手等。如果有 64 位整数数学可用,请使用上面指示的位掩码(所以 deuce=1,three=8,等等,直到 ace=2^36)并将卡片的值加在一起。如果与 04444444444444(八进制)相加的结果不为零,则这手牌是四张。否则,如果加上 plus 01111111111111 并与 04444444444444 相加得到非零值,则这手牌是三张或葫芦。否则,如果与 02222222222222 相加的结果不为零,则这手牌要么是一对,要么是两对。查看一手牌是否包含两对或更多对,将手牌值与 02222222222222“和”,并保存该值。减去 1,然后将结果与保存的值“相加”。如果非零,则这手牌至少包含两对(因此如果包含三对,则为葫芦;否则为两对)。

作为临别说明,为检查顺子而进行的计算还可以让您快速确定手中有多少张不同等级的牌。如果有 N 张牌和 N 个不同的点数,这手牌不能包含任何对子或更好的牌(当然可能包含顺子或同花)。如果有 N-1 个不同的等级,则手牌恰好包含一对。只有当有更少的不同等级时,才必须使用更复杂的逻辑(如果有 N-2,这手牌可能是两对或同类三;如果 N-3 或更少,这手牌可能是“三对”(得分为两对)、葫芦或同花四。

还有一件事:如果您无法管理 8192 元素的查找表,则可以使用 512 元素的查找表。如上所述计算位掩码,然后对数组[位掩码 & 511] 和数组[位掩码 >> 4] 进行查找,并对结果进行或运算。任何合法的顺子或平局都会在一个或另一个查找中注册。请注意,这不会直接为您提供不同等级的数量(因为在两次查找中都会计算第六到第十张卡片)但是对同一数组的更多查找(使用数组 [bitmask >> 9])只会计算插孔通过 ace。

关于用于测试扑克牌手牌的算法(4 到顺子)?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4040004/

相关文章:

javascript - 哪种数据结构最适合可快速搜索的文本数据?

regex - 哪些正则表达式支持捕获(而不是捕获组)?

java - 计算获胜几率 - 扑克机器人

javascript - 这种选择排序的实现有什么问题?

c++ - 如何在二维数组 ROW 中找到最小值和最大值?

math - float 学有问题吗?

language-agnostic - 记 "programmer"笔记的有效方法是什么?

javascript - 扑克牌生成器和评估器

在手中找到街道和同类的算法

c++ - 陷入二维逻辑