1、基本概念
棋局达到特定盘面,到底孰优孰劣,就需要一个数学模型来进行静态判定,这个进行静态判定的数学模型通常也叫评估函数。记忆中高等数学里有关多项式的内容中表示,不管多么复杂的评估函数,都可以用多项式逼近这个函数(泰勒公式?)。这个多项式是影响局面优劣的各种因素量化后的加权和。从而问题最终归结于如何选择影响局面优劣的因素及对应的权重,最后计算出多项式的值即为局面评价最终得分。
2、评估原则
选择对局面进行评估的知识因素时,有以下几点应该注意:
首先是如果不能确保用来评估的知识要素全面,那么就应该只选择那些有效知识,减少不必要的知识点,特别是有些因素是可以通过搜索体现出来的,如杀棋的搜索,棋子之间的威胁与保护等,是否要加入评估因素要多作测试才能确定优劣(如杀棋搜索就与知识的多少无直接关系仅仅与搜索深度有关,有些评估因素随着搜索深度的增加是可以反映出来的)。
其次要尽量让参与评估的知识要素相互独立(还是“正交”这个词?),避免对知识的评估产生交集,减少评估因素的相互影响,降低调试难度,例如兄弟兵、连环马等就是己方棋子相互保护的一种表现形式。
再次评估要素的得分值必须是准确的,不准确的知识量度也会导致出现问题,例如:空头炮在子力充沛时,分数很高,但是子力减少,则威力降低,很多人的空头炮就采用了上述方法进行评估,如果空头炮方子力很多但无法舒展,还强行保持空头炮,也是危险的,显然这也是棋手的基本常识。
最后是如何平衡知识与搜索效率问题,知识越多,搜索越慢,需要较多地平衡尽可能多的知识与尽可能高的效率的矛盾。
3、评估要素及权重
根据本人对象棋的理解及前人的经验,用于局面评估的知识要素,符合以上原则的准确而有效的知识至少应该包括以下几个要素,分别是固定子力值、棋子位置值、棋子灵活性与相互关系、棋子或者棋盘区域的威胁与保护及王安全评估与其它必要的动态调整等。这几个要素虽然不能覆盖影响棋局优劣的所有因素,但应该是主要因素且相关性不大,基本符合前面所说的对评估函数组成要素的要求。其中每一个影响要素的值又是由许多参数值构成的,例如固定子力值就包括7类棋子的值,将这些值线性地组合在一起得到最终的评估值。以下逐一叙述:
1) 最简评价,仅包括1固定子力值与2棋子位置值,是最基本的评估要素。此两项可在搜索结点变换局面makemove时增量计算,随着搜索功能的完成自然完成。此级为基础评估,除此外再无其它评估要素,棋力自然最弱,即使加大搜索深度,也无法提高棋力,大致对应初学者阶段,但用于解杀局是没有问题的(因为解杀局仅与搜索深度相关)。
2) 本部分主要是一种针对兵种类型数量变化的评估,站在某方防守的角度来评估各类防守缺陷,先为不可胜以待敌之可胜,如兑子后形成无车怕有车,缺仕(士)怕双车,缺相(象)怕炮攻等棋子数量变化带来的防守缺陷,提高基本的防御能力。另外由于中残局子力兑换后产生的兵种配置不佳问题。
3) 本部分主要是一种针对棋子之间相互制约关系的评估,评估各种特殊棋型。特殊棋型共分为以下两部分:
a) 第一部分评估兵种类型之间相互威胁与保护关系,如能够识别霸王车、连环马、担子炮及兄弟兵等棋型。
b) 第二部分是评估双方主力子力之间的互相联系、互相牵制的情况,以对方车为牵制目标,主要包括以下几种典型的牵制类型,车对车炮、车对车马、炮对车马及马象弱牵制、车对炮兵、马兵的弱牵制,此外还有炮的牵制,马象联合牵制等也需要细致考虑。
4) 本部分评估主要子力的阻碍与灵活性,使局面评估更加深入细致、更加精细。如能够马处边陲,车处僻地等情况。
5) 本部分为王安全评估,也是最为核心重要的评估部分,直接决定将帅的安全属性,是站在某方进攻的角度来进行评估。王安全评估又分为以下几个部分:
a) 典型攻势的评估,如当头与沉底空心炮 、沉底炮,炮镇窝心马及卧槽马配合明车进攻、车马冷招等进攻评估。
b) 王被牵制的评估,如车炮对王的牵制、马对王的牵制及将帅互相牵制等以将帅为目标的牵制评估。
c) 针对棋子与棋盘区域关系的评估,评估棋盘关键区域子力平衡与控制及多子联合攻势,是棋盘区域子力平衡的评估,主要是一种进一步评估先手攻势与风险,提高进攻与防御能力。如能够识别三子归边,九宫区域控制等
d) 其它王安全评估,进一步强化将帅安全性评估,识别将帅面临的终极风险,提高防御能力。
6) 这是最后一级评估,是对前面评估要素交集的补集,起到拾遗补缺的作用。暂时还未考虑好,不能确定具体是何种评估要素,是待改进部分。
关于权重:影响棋局优劣的要素权重又如何确定呢,最简单的做法通常是依赖于编程者的棋类知识,通过手动调整来确定参数,但由于工作量巨大及复杂性,手工调整很难达到全局最优。好一点的更有效率的做法是应用应用神经网络之类高大上的技术手法来自动整定权重参数(这个超出了能力范围需要再学习)。
4、各要素评估具体办法
关于分值粒度及权重的确定
为了加快运算速度,应尽量避免浮点运算。因此确定各要素评估中最小评估分值应至少为大于等于1的整数。假定最小评分单位为Vmin=1,则其它各要素评分值必须都可表示为该值的整数倍,如兵的价值为80*Vmin,车的价值为560*Vmin,比一个兵小的评估要素得分最小1分,如灵活性评估时,单子可达到的位置每多一个时加1分(最大得分应为车:9分)。如此同可以避免掉浮点运算,加快处理速度。
确定各要素权重系数时,假定最小评估要素的权重定为Wmin,则其它权重分别为Wmin的不同放大倍数,如下表所示:各要素权重系数
要素 子力价值 位置分 防守缺陷 特殊棋型 王安全 灵活性 其它 合计
权重 10 10 3 2 8 2 1
注:某评估要素中的细分要素权重应不大于它据在大类权重系数,如特殊棋型的评估,其主体权重为2,其细分要素有空心炮,窝心马,霸王车等,其每一个的权重均应小于等2,其它依次类推。
通过以上几级评估得到各级评估分值Ei(i=0 -5),其加权和即该局面下。某方总的得分值Ej(j=r或者b)。红方总价值Er,黑方子力总价值Eb,则:红方审局函数为Vr=Er-Eb. Vr为正,表示红方优势,越大越优势. Vr为零,表示双方均势.Vr为负,表示红方劣势,越小越劣势。黑方依此类推。另外,为了减少评估函数的计算量,提高搜索速度,参照某开源引擎的偷懒评估办法,以上每一级评估后以根据既定的边界条件作进一步简化评估,例如:第一级评估后,如果一方子力位置分已足够好,以至于可以产生beta了,就可以不再继续评估了;或者足够坏,再评估也没什么必要了:),此种情况皆可以立即返回结束评估。
1) 棋子核心价值评估
a) 静态子力价值
将帅分最大, 大约等于其它所有棋子的总值, 失去将帅, 意味着游戏结束。车大约等于马加炮, 稍大些可防止轻易兑子, 再多个士象或重要位置的兵, 便可以交换。马炮相当于两个士或象, 相当于四至五个兵, 炮稍大于马, 防止轻易交换, 炮换马兵可行, 炮换过河马可行。士相价值相当, 相当于两个兵。兵等于十分之一个车, 四分之一个马炮, 二分之一个士象。具体评分如下:
车:1000分
马:开局时400分、中局时450分、残局时500分
炮:开局时500分、中局时450分、残局时400分
兵:原位兵50分、未过河通路兵80分 过河兵100分,以后截止到对方生命线为止每下一路就加50分。双兵过河在中心三条纵线联手400分。
仕:200分 相:200分
帅:无限大,应不小于其它棋子总和。所有棋子皆可失去,唯将帅不可失去。
先手分:约等于一个开局原位兵。打将是绝对先手。
//以下是表格,格式乱了
兵种类型 帅 车 马 炮 仕 相 兵 合计
基本分 1000 400 500 200 200 50
单方数量 1 2 2 2 2 2 5 16
单方最大值 5000 2000 800 1000 400 400 250 9850
中局 +50 -50 适当加分
残局 +100 -100 适当加分
b) 位置势能。
不同位置上的棋子具有不同的分数,搜索时可引导子力逐渐靠近王周围,攻击敌方将帅。
以上为棋子固有能在makemove函数中增量计算(静态子力全价值与位置势能合并计算可加快评估速度)。
其值可作一般裁剪的依据。
2) 针对防守缺陷的评估
这是一种针对兵种类型数量变化的评估,如兑子后形成无车怕有车,缺仕(士)怕双车,缺相(象)怕炮攻等棋子数量变化带来的防守缺陷。缺一个士,则造成另外一个士为弱士、缺士怕车、马、卒、单缺象要受到惩罚、无车怕有车、缺象怕炮等。
3) 特殊棋型的评估
l 我方进攻子力与敌方王之间的关系
n 空心炮、窝心马、沉底炮、当头炮攻势评估,我方进攻子力与敌方王之间的关系。帅(将)、双仕(士)都在原位,这种情况要判断空头炮、炮镇窝心马和沉底炮;帅(将)在原位,双仕(士)从一边包围帅(将)(士要向自己相对势力较强的一边开口:简单将四个区域的大子子力价值相加,取自己相对势力较强的区域作为开口区域),这种情况要判断当头炮、左右沉底炮和车封帅(将)门(注:以“红下黑上”这个固定的棋盘方位来规定左右)。评估空头炮时,关键是要有子力配合,看大子的数量,如果子力众多,则可能借助空头炮取势;看双车是否健在,以及它们的灵活性;炮的位置,一般来说位置越高,对敌人的威胁越大;王在横向的自由度。当头炮及镇住窝心马的炮,炮离敌方王越近越有价值。空头炮、沉底炮,炮离敌方王越远越有价值。
l 牵制的评估
² 牵制对方将帅或车时,如果被牵制子有价值且没有保护(被目标子保护不算),那么牵制是有价值的,如果牵制目标子是车,不同于帅(将),要求车也没有保护时才有牵制价值。
² 马象牵制(不常见牵制类型),被牵制子没有保护时有牵制价值。
² 炮对马的牵制、炮对象的牵制、如果牵制的是车或者马(注,炮对炮造不成牵制)有价值。
l 威胁与保护评估:
² 我方同兵种之间的互相保护评估如霸王车、连环马、担子炮、兄弟兵,我方不同兵种之间的保护评估;双方兵种之间的相互威胁评估等。
² 直接威胁将帅时,完全解将至宁静局面后再评估
² 威胁其它单子时,适当调整子力价值表来体现。
² 威胁盘面格子时,为控制评估,见以下控制九宫的评估部分。
4) 区域子力平衡与王安全的评估
一般先手:50分。对方只是单纯出子,这步棋的性质就是前面所说的先着效率,相当一个原位兵。轻度威胁:100分。中度威胁:200分,严重威胁:400分,极度威胁:800分。
针对“三子归边”问题的子力区域平衡的评价
审局的作用,当引擎稳定后,对杀棋棋步进行测试,我们会发现,能否搜索出杀棋,跟引擎是息息相关,跟审局则是关系不大,但是,盘面危险度的认识,却跟审局息息相关,所以,我们得出一个结论,审局,只是评估危险度,不要让审局承担提前发现杀棋的工作,多在引擎本身找找原因。
王威胁>倾向性引导>棋型。
棋型即棋子摆放位置,倾向性引导为子力组合和运子方向,王威胁是对9宫的进攻情况。三者分数如上所述。王威胁模型,对9宫的威胁,通过攻击点的个数和程度来表示。例如,(炮)->(车)->[士]->[王],这样对9宫的攻击点有两个,因为车炮都双重攻击,所以被攻击的两个点的威胁度很高,(炮)->(马)->[士]->[王]可以有4个攻击点,但是威胁度都比较低,子力组合可以跟攻击点的威力有一定挂钩。
王被威胁的程度=f(进攻的子力组合,进攻的点),对王的威胁评估,只需寻找出上述两个参数,即可查表得知目前被威胁的程度。这种评估应该是相当准确的。
必需建立以将帅安全为核心的审局模型,对九宫的威胁,利用控制九宫位置分提示车马兵攻击王周围,依赖搜索完成).
位置 04 14 03 05 13 23 24 15 25 纵2-6横0-4 合计
得分 1 0.5 0.5 0.5 0.2 0.2 0.2 0.2 0.2 0.1
放大10倍后 10 5 5 5 2 2 2 2 2 1
最高分值 200
两子及三子归边攻势:两子攻势:典型的如缺仕双车(或车兵)杀,缺象怕车炮,缺仕怕车马等
三子归边攻势:首次有沉底炮、其次车可做炮架或进入了可以助攻的区域、最后马也进入了可以助攻的区域。牵制对方将帅形成的攻势
5) 灵活性的评估
灵活性评估因素:花心如果被自己一方别的子力占据,则阻碍了双士的连环性
车的纵横的自由度(大于6则很灵活,可以左右逢源;大于3,则比较灵活机动,否则扣分);如果纵向有自己的一个非过河兵阻碍着,要惩罚
马的灵活性很重要:如果没有好的着法就要扣分,如果马在边上,并且被对方车或者卒憋住马腿,则要严重扣分
计算动能时,只计车马炮的动能,且不考虑威胁或被威胁的位置限制。
车 马 炮 兵 将 仕 象 合计
实际可动步(平均) 17 8 17 3 20/9=2.2 (8/5)=1.6 (16/7)=2.3
圆整后: 17 8 17 3 2 2 2
灵活性系数:3 4 2 0 1 1 1
最大动能(252) 108 64 68 0 4 4 4
为简化起见,车马炮的动能皆放大至整数值,以避免浮点计算。 .
Ek=L/L0.其中L为棋子实际可移动步数,L0为棋子最大可移动步数.
6) 控制与威胁评估
威胁势能 = E0(黑损失)/E0(红)(当吃子时) 或 (E0(红损失)-E0(黑损失))/E0(红)(当子力交换时).(MVV/LVA算法)
7) 其它必要的评估知识
大势判断能力的评估,形势判断的优劣,背后是高超棋力的实力支持,需要开中残局象棋经验的全面积累。在这一点上局面型棋手要优于战术型棋手。例如对攻击力与威胁的认识,产生攻击威胁必然是因为对局者阵形存在着薄弱环节,比如某个保证将帅安全的重要点位缺乏防守,或是强子所处位置闭塞,失去灵活性。当处理对方的攻击威胁的时候,一定要有转换的思路。下棋是一人走一步,当局面处于平衡的时候,敌人对我形成攻击,在另外一处我也必然也对其形成了同等量级的威胁,例如对方攻击我方弱马,我能不能考虑弃子?我子都不要,对方这个威胁分就没有了,而我对他的威胁还保留着,这里我得到200分,我于另外的地方落子,之后对方即使只需花一步棋去吃我方弃子,这里我方又得到两个行棋度数,价值100分。如果在这个阶段我还能谋个兵卒捞个士象什么的,所得到的价值就已经不在一马之下,可以用精妙弃子来形容了。所以实施攻击时有三项原则。第一、对方阵形中有了真正的弱点才能进行攻击。第二、攻击要有充足的兵力和迅急的速度。第三、注意对方弃子转换的下法。对方威胁等级越高就越需要弃子处理,但是当面临极度威胁的时候,己方将帅危在旦夕,对方杀着呼之欲出,这时已经不是给对方一些好处就能妥善解决的事情。只能与其对杀,只要速度,不惜一切。
此外控制子力交换(如避免兑子后双马位置不佳,兑子后子力明显落后取胜或谋和的机会减少),保持先手优势(先手分,大约为半个兵的价值,能够消除奇偶层估值摆动问题)及兵卒的细调(不过河的兵,如果河对岸没有被对方控制,那么给予奖分,过河的兵,如果有保护,那么给予奖分)等也是要考虑到的评估知识点。
5、其它因素对评估函数的影响及调整
a) 开中残局各阶段的影响
静态函数只是简单的根据盘面情况由公式给出红黑方棋力的绝对差。而缺乏战术上的思考,棋手在对局中心中往往有个局势的概念,既己方是处于优势还是劣势,是该进攻还是防守,这很大程度上决定了棋手的出棋着法。比如一步换子着法,在优势的情况下多数情况下棋手为选择换子而在劣势的情况下则相反。但是传统静态函数仅是红黑方得分的绝对值差,由于缺乏局势的概念不会根据优劣形势做出灵活的判断。因此,局面评估函数应该根据局势的变化趋势动态地做出调整。如优势谋胜,劣势谋和,残局马胜炮等。
预评估当前局势处于开、中、殘哪一阶段,相应调整某些分值。如殘棋马胜炮,兵卒升值等。不同阶段的盘面各类影响因素是不同的, 不同阶段采取的策略是不同的, 开中残差异是很大的。对于权重的调整也是与开中残局有关的,例如,开局注重占据有利位置,可以适当提高子力位置价值的权重,残局时则更加注重子力配合作战及王的安全性评估,强化将军与解将的能力。
开局可以通过完善的开局库来解决问题,但也可以通过子力位置分通过一些简单评估来搜索较准确的棋步。
残局通过调整子力位置分表, 判断子力组合,控制好搜索的危险程度,防止出现盲目进攻的现象。
中局是比较复杂的,基本原则应该是集中力量搜索杀棋或者扩大子力优势。
depth=1时进行杀棋知识评估仅只局限于depth=1的杀棋知识
depth>=2时进行分层次打分。比如: 三子归边的判断, 我们通过以下三种层次评分
(a) 有沉底炮, +分 (depth=3)
(b) 有沉底炮和车可做炮架, +分 (depth=2)
(c) 有沉底炮和车并且马进入了可以助攻的区域, +分 (depth=1)
选择有效的必须的知识是评估的基本原则:
a. 准确的杀型,利用位置分值和对九宫的控制等来引导提示车马兵攻击王周围,依赖搜索完成
b. 模糊的杀型,如 当头炮 (空头炮,镇中)、沉底炮 (三子归边)、双车杀等。
c. 子力组合,只做会引起问题的子力组合判断,如兑子后双马不佳
残局阶段特定棋形组合的评估,残局阶段固定子力组合的评估如例胜例和定式(只打分不给出步法)。
b) 进攻与防御状态对评估函数的影响
c) 开局与残局的特殊处理与强化
当无法对王造成威胁时,子力组合和运子就非常重要了,运子在特定盘面,都有一定的倾向度,所以,搜索前通过调整子力表,即可对运子造成影响,当然,需要准确评估还是eval_r()可靠,如兵卒的分数调整。子力组合的情况,子少时,就是残局了,中局时,车马马是不如车马炮的,这些都需要有一定提示。
如果对方的大子很少了,就要增加兵卒的影响因子。很多棋型的合理性,在使用了子力表后,在计算中是可以体现出来的,但是,单车和单车士象全这种子力组合,却是无法通过子力表得知的。对于这种类型的残局,可以通过使用知识型残局来解决(如果是用到完整的残局库的话,则不在局面评价这个讨论范围内,而应是专门的残局库制作与应用的专题了)
6、评估模块的组织与主要评估步骤
0、在position.cpp里增加了保护判断函数::protected();用于判断特殊牵制棋型时判断牵制目标子是否存在保护,已完成未调试。
1、evaluate_init()为局面预评估函数。约定盘面红下黑上!先断言不会被将军(需做到进入前总是解将),判断棋局阶段,次扫描收集各类棋子相互牵制信息,再扫描各棋子能达到的位置(可达到格子、捉住或威胁某个棋子即威胁与保护属性),顺带完成灵活性评估与九宫区域控制评估。局面预评价功能((约定盘面红下黑上!)
1.1、判断局势处于何种阶段,开中局还是残局阶段(计算各种棋子数量,按照车=6、马炮=3、其它=1相加)根据不同阶段做些必要的参数或分数值调整。
1.2、判断各方进攻防御状态,分红左红右及黑左黑右4个区域统计,以后还可用于判断多子归边攻势(计算过河子数量,按车马2炮兵1相加),根据进攻还是防守状态做些必要的参数或分数值调整。
1.3、扫描收集红黑双方对将帅的牵制信息,填充被牵制子信息结构,以后可用于判断是否可移动及对其它棋子的保护是否真实有效(如果处于被牵制状态是移动受限的,实际上对保护子的保护是虚假无力的)。
1.4、扫描所有棋子可移动情况,填充ei中有关的威胁与保护、灵活性及控制棋盘区域的有关信息,以后可用于各种评估
1.5、检查预评价是否对称
2、扫描单方所有棋子可移动情况,填充ei中有关的威胁与保护、灵活性及控制棋盘区域的有关信息,以后可用于各种评估。区域子力平衡,识别多子归边攻势,在此顺便完成本阶段的评估。
2.1、扫描棋子位置,记录各个区域的进攻子数量与价值,判断各方进攻防御状态。
2.2、进一步扫描下一步可达到位置,根据可达到位置所在区域进一步细调各区域进攻力量
2.3、控制棋盘格情况:可用于判断九宫格所受到的威胁情况,可用于棋子灵活性判断。
2.4、威胁对方棋子:可用于判断是否调整对方受威胁棋子子力位置分
2.5、保护我方棋子:可用于判断是否调整我方受保护棋子子力位置分;可用于判断一些特殊棋型如霸王车、连环马等
3、扫描收集红黑双方对将帅的牵制信息,填充被牵制子信息结构,用于判断是否可移动及对其它棋子的保护或者威胁是否真实有效(如果处于被牵制状态移动是受限的,而且对其它棋子的保护与威胁是虚假无效的)。
3.1、炮牵制:我方炮用超级远程炮吃子的方式能吃到对方将则构成牵制
3.2、车牵制:我方车用炮吃子的方式能吃到对方将则构成牵制
3.3、空心炮牵制:我方炮用车吃子的方式能吃到对方将,则构成空心炮牵制:这个这里不需要
3.4、马牵制:马脚有对方子,移动该子就可吃到对方将军,构成牵制
3.5、将帅互相牵制:我方帅用炮吃子的方式能吃到对方将则构成牵制,类似车的牵制
4、扫描所有棋子可移动情况,填充ei中有关的威胁与保护(与棋子相关)、灵活性及控制棋盘区域(与棋格或棋盘区域相关)的有关信息,以后可用于各种评估。(本步骤中是否要根据牵制信息过滤掉不能移动的棋步,过滤掉因被牵制可保护或威胁实际上却起不到保护与威胁作用的无效棋步?)。
5、检查预评价是否对称(实际每一个评价要素都应该有对称是否的检查)
2、王安全性评估为核心评估函数。主要包括以下四大控制和进攻势力:
2.1、评估王与其它棋子位置关系在攻势上的体现
//2.1.1、炮的攻势评估 //1、当头与沉底空心炮 //2、窝心马 //3、沉底炮 //4、当头炮
//2.1.2、王被牵制评估 //1、车炮对王的牵制 //2、马对王的牵制 //3、将帅互相牵制情况
2.2、评估棋盘关键区域子力平衡与控制及多子联合攻势
//2.2.1、九宫控制力(此部分可提前至预评价模块中棋子扫描时棋格或棋盘相关的评价部分)
//2.2.2、区域子力平衡,识别多子归边攻势(此部分可提前至预评价模块中判断进攻防御状态时处理)
3、特殊棋型评估函数,评估双方主力棋子相互牵制情况,以对方车为牵制目标,主要包括以下几种典型的牵制类型,其它牵制类型暂不考虑:
1、车对车炮 2、车对车马 3、炮对车马 4、马象弱牵制 5、车对炮兵、马兵的弱牵制
4、马车灵活性评估,已完成未调试(此部分提前至预评价模块中)。
5、单兵种评估共6个,已完成未调试。
7、参数调整与测试
基本评估功能完成后,就面临着局面评估函数中各类参数的调整与优化测试,此项工作复杂,工作量也大。主要可以采取的办法有以下几种:
7.1、 收集典型的样本局面,利用人类专家知识经验先做出较准确的局势判断,计算各评估要素得分值。根据得分结果判断调整,再与引擎eval结果比对,逐一调整。此纯手工操作工作量较大。
7.2、 利用其它强软的评估分数做参考来调整。
7.3、 利用人工神经网络来调整。
8、存在的问题及未来改进的方向
注:此文几年前一直躺在新浪博客私密博文中,今拿出来晒晒 🙂