我看到了这个跳棋游戏,我想知道AI是如何实现的。
我应该如何为检查员(草稿,妈妈,妈妈)实现AI ?有没有已知的算法?
非常感谢所有人。我很奇怪看到这个Tic Tac Toe游戏教程博客文章。
所以,我想要dama游戏算法的开源代码和博客文章..是否有任何有用的链接或任何doc文件..?请告诉我..
我看到了这个跳棋游戏,我想知道AI是如何实现的。
我应该如何为检查员(草稿,妈妈,妈妈)实现AI ?有没有已知的算法?
非常感谢所有人。我很奇怪看到这个Tic Tac Toe游戏教程博客文章。
所以,我想要dama游戏算法的开源代码和博客文章..是否有任何有用的链接或任何doc文件..?请告诉我..
Answers:
哦,我喜欢这些游戏!
因此首先,为了使计算机能够玩游戏,它需要:
让我们一次解决这个问题。
由于该板是8x8网格(但可以轻松缩放),并且每个网格空间可能仅存在于五个状态之一,因此让我们定义以下状态:
[EMPTY, WHITE_PIECE, BLACK_PIECE, WHITE_PIECE_PROMOTED, BLACK_PIECE_PROMOTED]
分别枚举到:
[0, 1, 2, 3, 4]
现在我们知道每个空间可以是什么,我们需要某种方式来表示所有空间,或者如果需要的话,可以代表木板。几乎每种强语言都将支持多维数组(每个元素都是保存数据的数组)。因此,请使用以下松弛码来定义我们的数组:
BOARD_ARRAY = array(8, 8)
这将为我们提供8 x 8的数组,我们可以在其中存储整数(我们之前的枚举):
(
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
)
现在您已经可以看到它开始看起来像板子了!我从没玩过youtube视频中提到的变体,但它似乎是从底部开始的两行白棋和从顶部开始的两行黑棋开始。这意味着当我们开始游戏时,我们的数组应如下所示:
(
[0, 0, 0, 0, 0, 0, 0, 0],
[2, 2, 2, 2, 2, 2, 2, 2],
[2, 2, 2, 2, 2, 2, 2, 2],
[0, 0, 0, 0, 0, 0, 0, 0],
[0, 0, 0, 0, 0, 0, 0, 0],
[1, 1, 1, 1, 1, 1, 1, 1],
[1, 1, 1, 1, 1, 1, 1, 1],
[0, 0, 0, 0, 0, 0, 0, 0],
)
(记住2代表'BLACK_PIECE',1代表'WHITE_PIECE')
因此,现在计算机具有可以使用的结构。步骤1完成!
假设您在前面摆放了一个实际的棋盘,与主玩家对战。如果您尝试移动他的一件作品,那么您会被拍打。如果您尝试以某种无法移动的方式进行操作,那么您将被打一掌。如果您试图作弊,那您就明白了。但是问题是,计算机却没有。因此,提供严格的比赛规则是我们的工作。
我们需要创建一种方法来检查给定的举动是否合法。这意味着我们首先需要某种方式来表示“移动”。一种方法是使用数组位置。例如,要将一块从[0,0]移到[0,1],我们可以创建一个函数,该函数将根据该移动来更新板。回到松弛状态:
MY_MOVE = array( [0, 0], [0, 1] )
上面的代码代表一块,从板的顶角向下移动了一个空间(假设0,0是左上角)。您可能还会注意到,我选择了使用多维数组进行移动。这是因为理论上碎片可能会在一圈中移动很多次(“跳动”其他碎片)。因此,让我们假设在0,1处有一个对手棋子,这意味着我们将在0,2落地:
MY_MOVE = array( [0, 0], [0, 2] )
很简单吧。程序应该理解,如果我们跳过一个空格,我们将跳过另一块(否则这是非法举动,并且应该引发错误)。现在让我们跳两段:
MY_MOVE = array ( [0, 0], [0, 2], [0, 4] )
这为我们提供了一种描述董事会任何举动的方式。好极了!现在,由于我不完全了解所讨论的确切游戏规则(尽管我今天玩过一些加拿大跳棋),因此您需要确定确切的移动合法性。到目前为止,良好的流程如下所示:
FUNCTION_FIND_ALL_LEGAL_MOVES( MY_BOARD ) Returns: array ALL_LEGAL_MOVES
FUNCTION_FIND_BEST_MOVE( MY_BOARD, ALL_LEGAL_MOVES ) Returns: array MY_MOVE
FUNCTION_DO_MOVE( MY_BOARD, MY_MOVE ) Throws: error ILLEGAL_MOVE Updates: MY_BOARD
repeat from start for each turn
上面的假设假设您可以循环遍历每件事情,以找到其所有合法举动,然后给出所有合法举动的集合,以某种方式选择最佳举动(此处为策略)。然后,此操作将应用于板,或引发错误。然后下一位玩家轮到他们。所以我们有一个会玩的AI!喜悦!继续。
简单的游戏很棒,因为获胜是由非常简单的状态决定的。黑板上没有白色的东西吗?好吧,我猜你赢了!当我们选择最佳举动以使我们更接近获胜条件时,这将在步骤2中实现。
要使智能AI变得非常智能,您可以保留一个数据库,该数据库将每个可能的板作为状态存储,并从每个可能的状态向可能的结局转移。
您还可以创建策略,例如:如果有一个乐段要跳,请保存该乐段,或者如果一个乐段能跳得比另一个乐段跳得多,那就跳。
那应该给您一个很好的起点,这只是从根本上无限可能性的一种方法。从理论上讲,您可以构建一个巨大的机器人来用蜡笔绘制图形,然后在图形上进行光谱分析以选择移动方式……但是这种方法不能很好地工作,也不能很快。这种方式在过去一直有效,并且运作良好(:希望能有所帮助!
Checkers是所谓的“已解决”游戏,因为我们可以计算出未知数的每一步。但这就是一整步的动作!因此,没有办法手动完成所有操作...如果只有一些...哦,对了,我们是程序员。拳头泵
SQL是用于存储所有这些看似无穷无尽的动作的绝妙工具。对于那些没有SQL经验的人,mySQL是免费(相当容易使用)的开源SQL Server。SQL用于管理数据库,有点像类固醇电子表格。它还能够保存大量数据并非常快速地使用它。
那么我们如何使用呢?由于我们知道如果板处于精确状态(每个板都处于某个位置),我们可以计算所有可用的移动并将其保存。例如:
+Board State+ +All Possible Moves+ +Best Move+
([0,0,1,2,3],[3..) ([0,1],[0,2]), ([7,6],[7,7],[5..) ([7,6],[7,7])
([0,0,2,2,3],[3..) ([0,1],[0,2]), ([7,6],[7,7],[5..) ([5,5],[5,4])
([0,0,1,3,3],[3..) ([0,1],[0,2]), ([7,6],[7,7],[5..) ([4,4],[4,3])
etc...
因此,当计算机需要移动时,它只需在数据库中查找板状态(存储为主键),然后可以选择最佳移动(应该无与伦比),或选择其他移动之一以使操作更友好AI。
太好了,现在让我们建立一个数据库。首先,我们需要计算每个董事会状态。如果有人想花费一些时间并解决它,那将是一个很大的麻烦循环,这真是太棒了。将数组视为一个大数字,然后向上计数(以5为底数(0、1、2、3、4)除外),并规定每个玩家只能拥有16个。
在这一点上,我们应该存储所有板状态,并且可以计算所有可能的移动。
一旦计算出所有可能的动作,便是寻找最佳可能动作的有趣部分。这就是我的知识开始不足的地方,诸如Minimax或A *之类的东西开始发挥作用。抱歉,对此我无能为力了:/
在游戏中的任何时候,玩家的可能动作数量都非常低*(大约5),这意味着可以考虑一些前进动作,评估每个可能动作并选择最佳动作。
这种方法称为minimax(维基百科)。
要实现极小极大值,您需要一个评估功能,该功能返回给定板布局和玩家的得分。对于草稿,幼稚的实现将是一个功能,该功能为玩家活着的每一块都返回一个积分。
最小极大决策树的可视化(来自维基百科文章)。左下方是转数。每个叶节点都有一个评估分数,该分数被反馈到树上以做出决策。
*
但是草稿是分支因子最高的游戏,已经被彻底解决。