斗地主游戏的初期版本目前为止大概已经完成的一半了...
还剩下最麻烦的部分(AI)没写,写这篇博文主要是想理一下基本的思路,然后把这一部分也搞完.
先上一个目前的进度截图纪念一下好了
经过较长时间的冥思苦想,包括网上找资料...(网上关于斗地主AI的资料很少.)
终于想到了一个大概可行的办法~先写出来试试吧..
斗地主的AI部分主要分为两块:
一个是主动出牌.(自己是第一个出牌的,或者上一把打出的牌没有人要,又轮到自己了) ---这时候就需要从当前的手牌中选取一道合适的牌打出.
怎样选取呢?这正是要解决的问题.
还有一个是被动出牌,也就是根据上家的牌,从自己的手牌中选取一道比较好的牌打出.
这一个比第一个要麻烦一点,因为涉及到了大小的比较,同队之间的配合等等因素.
怎样从当前手牌中选取一道比较科学的牌呢?
如果我的手牌中有单牌,有对牌,有炸弹,刚上来肯定是出单牌或者对牌,而不是炸弹,(因为炸弹是用来炸别人的)
所以要想得到一个比较好的出牌,就必须遵循一定的规则
(Nothing can be accomplished without norms or standards.)
.....
我的想法是这样的
首先应该扫描整幅手牌,看一下有哪些类型的牌.
这一过程"斗地主业界"称之为拆牌
比如 334445778910JJJJQK2这样的一副烂手牌.
凭借我多年的打牌经验,我觉得应该这样拆:
[JJJJ(炸弹)] [33444(三带二)] [5,8,9,10,Q,K,2(单牌)] (不过这破手牌,怎么拆也是输~)
下面就来看一下怎样分牌才能达到我们想要的效果~
考虑采用4个辅助数组来拆牌
我们将它分成如下的四个数组.
(0)--34578910JQK2
(1)--347J
(2)--4J
(3)--J
然后可以通过这四个数组,得到一个较好的出牌.
首先,我们定义一些牌型组,每个牌型组放该类型的牌,牌型组包括:单牌组,单顺组,对牌组,双顺组,三牌组,三带一组,三带二组,炸弹组,火箭组.
(这里为什么没有四带二组,飞机组呢,因为我觉得这两种牌没什么震慑力,就是一搅屎棍子~)
下面是我总结的一些规律:
- 在四个数组中,下面的每个数组都是上面数组的子数组.(所以,我们可以由下往上依次扫描各个数组)
- 如果第四个数组中有元素,则该组手牌中一定有炸弹.(我认为炸弹的作用非常大,所以遇到炸弹应该直接提取出来)
- 第四个数组变为空时,就扫描第三个数组,第三个数组中的元素一定对应三张相同的牌.(根据这些牌,可以找到三带一,三带二等)
- 另:[鼓励三带一,三带二,但不鼓励飞机,四带二,这样一是可以降低复杂度,二是四带二没有什么价值].
- 找单牌(存在与第一个数组中,而不存在于第二个数组中的,一定是单牌,找出单牌后,还应该判断能不能组成单顺)
- 找双顺(从第二个数组中找,但是双顺最好不要拆三牌,因为三牌的价值大于双顺)
- 找单顺,肯定是在第一个数组中找~(要单顺还是要对牌是一个比较纠结的问题,可以制定一个标准)
- 最后总结一下找牌的顺序,就可以开始编码了.
(顺序很重要,好的顺序才能拆出好的牌,下面是我总结的拆牌顺序~)
0.找一下有没有火箭,有的话放入火箭组.
1.找出所有的炸弹,放入炸弹组.
2.找出所有的单牌,放入单牌组.
3.找出三牌,放入三牌组.
4.找出所有的对牌,放入对牌组.
5.找出单牌组中的单顺,放入单顺组.
6.找出对牌组中的双顺,放入双顺组.
7.将三牌组与单牌组的元素依次结合,放入三带一组.
8.将三牌组与对牌组的元素依次结合,放入三带二组
9.注意:三带一不能带大小王,单顺不能带2和大小王,双顺和三顺不能带2.
基于上面的步骤,我们就可以找到一个较好的出牌了~
0.如果是主动出牌,扫描顺序为:
单牌组,单顺组,对牌组,双顺组,三牌组,三带一组,三带二组,炸弹组,火箭组.
出第一个找到的牌即可.
1.如果是被动出牌.
----0.首先找同类型组中比上家大的牌,如果有,出牌.
----1.如果没有,就评估一下是否值得出炸弹,如果值得,则到炸弹组中找,出炸弹.如果不值得,pass.
----2.没有炸弹,就到火箭组中找,出火箭.没有火箭,pass.
注意:暂时没有考虑同队伤害.
原文地址:https://www.cnblogs.com/huangliang-hb/p/8858120.html