CodeCombat 高级指挥

Python 批量控制与状态记忆

LEVEL 3

标准操作规程 (Standard Operating Procedure)

战术逻辑分析

指挥官,我们遇到了一个大问题!以前我们只有一个士兵,我们可以叫他"小明"(soldier1)。 但现在我们有一支军队!如果我们还要一个个叫名字:"小明攻击!"、"小红攻击!"、"小刚攻击!"... 代码会写到天亮。

解决方案:神奇的代号 "Target"

我们不再叫名字,而是给每个人发一张通用的任务卡。
event.target 就像一面镜子。谁拿着这张卡,task 就是指谁。
如果是 soldier1 拿着卡,target 就是 soldier1;如果是 munchkin 拿着,target 就是 munchkin。

Event.target

"谁触发事件,谁就是Target"

1
game.addDefeatGoal()
添加胜利条件:击败所有敌人
2
soldier1 = game.spawnXY("soldier", 50, 30)
生成士兵1号
3
soldier2 = game.spawnXY("soldier", 50, 35)
生成士兵2号
4
soldier3 = game.spawnXY("soldier", 50, 40)
生成士兵3号
5
munchkin1 = game.spawnXY("munchkin", 25, 30)
生成我方矮人1号
6
munchkin2 = game.spawnXY("munchkin", 25, 35)
生成我方矮人2号
7
munchkin3 = game.spawnXY("munchkin", 25, 40)
生成我方矮人3号
8
9
def fightEnemies(event):
定义通用战斗逻辑,一定要带 event 参数
10
while True:
保持循环执行
11
# 这里的关键点!不要写死名字!
12
unit = event.target
谁执行这个函数,unit就是谁
13
enemy = unit.findNearestEnemy()
让当前单位找它自己的敌人
14
if enemy:
如果发现敌人
15
unit.attack(enemy)
让当前单位发起攻击
16
17
# 批量指派任务
18
game.setActionFor("munchkin", "spawn", fightEnemies)
命令所有"munchkin"类型单位执行战斗逻辑
19
game.setActionFor("soldier", "spawn", fightEnemies)
命令所有"soldier"类型单位执行战斗逻辑
LEVEL 4

中心队形 (Center Formation)

战术逻辑分析

天黑了,我们需要让分散在地图四个角落的士兵集合到中间的篝火旁取暖。

  • 我们不需要对每个士兵喊话,而是使用广播系统 game.setActionFor
  • 篝火的坐标是 (40, 36)
  • 只要士兵一出生(spawn),他们的大脑就会接收到指令:走向篝火!
1
def centerFormation(event):
定义集合逻辑
2
# 获取当前接收指令的单位
3
unit = event.target
从事件中获取目标单位
4
# 走向地图中心的篝火
5
unit.moveXY(40, 36)
移动到坐标 (40, 36)
6
7
# 生成四个分散的士兵
8
game.spawnXY("soldier", 16, 57)
左上角士兵
9
game.spawnXY("soldier", 15, 13)
左下角士兵
10
game.spawnXY("soldier", 63, 13)
右下角士兵
11
game.spawnXY("soldier", 67, 57)
右上角士兵
12
13
# 统一设置行为
14
game.setActionFor("soldier", "spawn", centerFormation)
所有soldier出生即执行centerFormation
LEVEL 5

瓶颈 (Bottleneck)

战术逻辑分析

我们需要守卫一条重要的林间小道。这里的战术叫做“弹力带战术”

1
记住岗位 (Memory)

士兵一出生,必须先用变量 startX 记下自己站在哪里。这是在 while True 循环外面做的。

2
出击与归位 (Loop)

如果有敌人 -> 冲出去打!
没敌人了 -> 回到 startX 那个位置。就像弹簧一样缩回去。

startX = unit.pos.x

loop:
  attack() OR moveXY(startX)
1
def defendLane(event):
定义防守巡逻逻辑
2
# 记住为目标创建一个变量,要记住:
3
unit = event.target
确定是谁在执行任务
4
# 保存单位的起始pos.x(重要:在循环外记录!)
5
startX = unit.pos.x
记下初始X坐标,作为“家”的位置
6
while True:
开始无限循环巡逻
7
enemy = unit.findNearestEnemy()
寻找最近的敌人
8
# 如果有敌人
9
if enemy:
发现入侵者!
10
# 单位(unit)调用攻击(attack)方法来攻击敌人:
11
unit.attack(enemy)
离开岗位去攻击
12
else:
如果没有敌人(安全了)
13
# 让单位移回起始位置的x和y坐标。
14
unit.moveXY(startX, 16)
回到刚才记下的startX位置
15
16
game.spawnXY("soldier", 9, 16)
生成士兵A
17
game.spawnXY("soldier", 30, 16)
生成士兵B
18
game.spawnXY("soldier", 54, 16)
生成士兵C
19
game.spawnXY("soldier", 75, 16)
生成士兵D
20
21
# 将处理器函数defendLane添加到所有 "soldier" 的"spawn"事件上
22
game.setActionFor("soldier", "spawn", defendLane)
所有士兵出生即开始巡逻