游戏 AI - 5

游戏 AI 的三要素

Posted by Kang Cai on July 9, 2020

从软件工程的角度来看,游戏总是因为编程糟糕而受到批评:它们使用技巧、神秘的优化和未经验证的技术来获得额外的速度或简洁的效果尽管游戏引擎可能会被重用,但游戏玩法代码通常不会,或者至少不会在编写时考虑到这一点,而较大的时间压力意味着程序员通常会为了完成游戏而去做任何他们需要做的事情,游戏 AI 也不例外。

在游戏中的 AI 和其他编程行业或学术界认为的 AI 之间存在着巨大的鸿沟。根据我的经验,游戏的 AI 等同于 “特殊技巧+启发式方法+算法”,其中黑客表示临时的解决方案并表现出整洁效果,启发式并不是必需,算法表示恰当的实现)。本书的大部分内容针对的是最后一组,即算法,因为这些技术我们可以概括、分析、检查、在多个游戏中使用,并构建到一个 AI 引擎中。但特别的解决方案和启发式方法同样重要,可以像很复杂的算法一样为角色注入活力

一、特殊技巧

俗话说:“如果它看起来像鱼,游起来也像鱼,那它可能就是鱼。”我们通过充分准确地复制行为来理解它。

作为一种心理学方法,它与行为主义心理学学派有关,但已被很大程度上取代。时代变了,人工智能的心理学含义也变了:通过制造一台机器来复制人类的智能,这在过去是可以接受的,但现在这被认为是拙劣的科学。有充分的理由;毕竟,建造一台能够熟练下国际象棋的机器需要计算数百万棋盘位置的算法,人类根本做不到这一点。

另一方面,作为游戏 AI 工程师,我们获得报酬并不是为了对现实或心灵的本质感兴趣;我们想要的是看起来行为正确的角色。在大多数情况下,这意味着可以直接从人类的行为出发,并试图找出在软件中实现它们的最简单的方法。游戏中好的 AI 通常都是朝着这个方向工作的。开发人员很少会在构建一个伟大的新算法后问自己:“那么我可以用它做什么?”相反,你从一个角色的设计开始,然后运用最相关的工具来得到结果。这意味着游戏 AI 的实现可能无法被判定成是 AI 技术。一个简单的随机数生成器应用得当,可以产生大量的可信度,而生成随机数本身不是一种人工智能技术。在大多数语言中都有获得随机数的内建函数,所以当然没有必要给出它的算法,但它在很多情况下都能发挥作用。

另一个创造性AI开发的好例子是《模拟人生》,虽然在表面之下有相当复杂的事情发生,但许多角色的行为是与动画沟通的。去掉角色动画,人工智能看起来就没那么令人印象深刻了。在《星球大战 I》中,被惹恼的角色对其他角色会借机撞击。《Quake II》引入了手势指令,现在被广泛应用于第一人称游戏中,角色和玩家可以将他们的敌人赶走。所有这些都不需要重要的AI基础设施,他们不需要复杂的认知模型、学习或神经网络,他们只需要几行代码在适当的时间安排动画即可。

经常注意那些简单的东西,它们会给人以智慧的错觉。如果你想要创造富有情感的角色,是否可以在你的游戏中添加一些情感动画(比如神庙受挫的摩擦,或者跺脚)?在适当的地方触发这些比试图通过角色的行为表现他们的情绪状态要容易得多。你有一系列的行为让角色从中选择吗?这个选择会涉及到许多因素的复杂权衡吗?如果是这样的话,那么尝试一种完全随机选择行为(可能每种行为都有不同的概率)的 AI 版本可能是值得的。你也许能分辨出其中的差别,但你的客户可能看不出来;因此,在编写复杂版本之前,请先试一试。

二、启发式方法

启发式方法是一种经验法则,一种在许多情况下可能有效但不太可能全部有效的近似解。

人类一直在使用启发式方法。我们不会试图计算出我们行为的所有后果。相反,我们依赖于我们在过去发现的普遍原则(或者我们被教导的,甚至被洗脑的,都差不多)。它可能包括一些简单的东西,比如如果你失去了什么东西,就会重新寻找它,也可能是指导我们生活选择的启发式,比如永远不要相信二手车推销员。

启发式已经被编入这本书中的一些算法中,对 AI 程序员说启发式通常会让人联想到寻路或目标导向行为的画面。除此之外,这本书中的许多技巧都依赖于可能并不总是明确的启发式。在决策、移动和战术思维(包括桌面游戏AI)等领域,速度和准确性之间存在权衡。当精确度被牺牲时,通常是用启发式代替对正确答案的搜索。

广泛的启发式可以应用于不需要特定算法的一般 AI 问题。

在我们常年使用的吃豆人例子中,幽灵会在一个路口走一条通往当前目标的路线。他们不会试图计算出最佳路线:最短或最快的路线。这可能是相当复杂的,并涉及回到自己,这可能最终是多余的,因为球员的位置继续改变。但是经验法则(沿着目标的当前方向移动)在大多数情况下都是有效的,并为玩家提供了足够的能力去理解幽灵的移动并不是完全随机的。

在《魔兽争霸》(以及随后的许多RTS游戏)中,有一种启发式方法,可以让角色稍微自动向前移动,这样他们就可以与站在距离角色更远的地方的敌人交战。虽然这在大多数情况下是合理的,但并不总是最好的选择。当敌人靠近时,许多玩家会因为全面的防守结构被破坏而感到沮丧。之后,RTS 游戏允许玩家选择是否开启这种行为,比如《魔兽争霸》、 DOTA1 以及很多其它后来的游戏里的 H 键。

在许多战略游戏中,包括棋盘游戏,不同的单位或棋子都有一个单独的数值来表示它们有多好。在国际象棋中,兵通常设成1分,主教和骑士设成3分,车设成5分,皇后设成8分。这是一种启发;它用一个数字代替了对一个单元能力的复杂计算。而数字可以由程序员预先定义。AI 可以通过简单的数字相加来计算出哪一边是领先的。在 RTS 中,它可以通过比较数量和成本来找到最具价值的进攻单位,通过操纵这个数字可以实现许多有用的效果。

没有一个算法或技术来解决上述类似问题,你不会在已发表的 AI 研究中找到它,但这是 AI 程序员的饭碗

启发式方法不断推陈出新,在处理问题的初期,它们是很好的着手点,接下来会介绍一些常见的启发式方法。

2.1 先做条件最严格的事情

给定世界的当前状态,需要选择集合中的一个个体,所选个体应是最少满足指定状态的个体。

例如,多队玩家控制角色与一群敌人交战。其中一个敌人穿着一种只有一支步枪才能穿透的盔甲,玩家的一队角色有这把步枪,当他们选择攻击谁时,最受约束的启发式开始发挥作用,因为只有一队角色可以攻击这个敌人,所以这是这队角色应该采取的行动。即使这些角色的武器在对付不同的敌人时更强大,也应该让他们的队友来对付其他的敌人。

2.2 先做最难的事情

最难做的事情往往意味着会影响很多其它行为,最好先做这件事,而不是发现简单的事情进展顺利,但最终却被浪费了。

例如,一支军队有两个空建造位置,电脑准备安排创造四个兽人战士和一个巨大的石头巨魔,兽人占用1/4建造位置,巨魔占用1个建造位置,它希望以平衡的阵容结束,它应该如何分配建造位置给小队?石头巨魔需要的插槽最多,所以最难分配,应该把它放在第一位。相反,如果兽人先被分配,他们将会在两个小队之间保持平衡,在每个小队中留下半个巨魔的空间,但是巨魔却无处可去。

2.3 先尝试最有希望的事情

如果 AI 有很多选择,通常可以给每个选项一个非常粗略的分数,即使这个分数是非常不准确的,尝试按分数递减顺序的选项将比纯粹随机尝试提供更好的表现。

三、算法

所以我们来到 AI 程序员的最后三分之一的工作:构建算法来支持有趣的角色行为。特殊技巧和启发式方法会帮你走很长的路,但仅仅依靠它们意味着你将必须得不断地重复造轮子。一般的 AI,如运动、决策和战术思维,都受益于经过试验和测试的方法,这些方法可以不断重复使用。

这本书就是关于介绍这些算法的,接下来的几篇文章将介绍其中的大量技术。但要记住,对于每一种 “复杂算法看起来是最好方法” 的情况,可能会有更多更简单的特殊技巧或启发式方法来完成工作