CodeCombat 状态与循环控制

函数、生命值、金钱与中断(56-66关)

第 56 关

Kithgard附魔师 (Kithgard Enchanter)

战术思路分析:定义魔法咒语

英雄失去了靴子!你必须定义自己的移动函数,就像是给英雄施加了一个“移动咒语”。

关键:函数定义 (`def`)

定义函数使用 `def 函数名():` 结构。函数体内的代码描述了移动逻辑:读取当前位置,计算新位置 (`+ 12` 或 `- 12`),然后使用 `hero.moveXY` 移动。

def moveRight():
  x += 12

Python 程序解法

1
def moveRight():
定义向右移动 12 米的函数
2
x = hero.pos.x + 12
计算新的 X 坐标
3
y = hero.pos.y
Y 坐标保持不变
4
hero.moveXY(x, y)
移动到新位置
5
6
def moveUp():
定义向上移动 12 米的函数
7
x = hero.pos.x
X 坐标保持不变
8
y = hero.pos.y + 12
计算新的 Y 坐标
9
hero.moveXY(x, y)
移动到新位置
10
11
def moveDown():
定义向下移动 12 米的函数
12
x = hero.pos.x
X 坐标保持不变
13
y = hero.pos.y - 12
计算新的 Y 坐标
14
hero.moveXY(x, y)
移动到新位置
15
16
moveRight()
调用函数,执行右移
17
moveDown()
调用函数,执行下移
18
moveUp()
调用函数,执行上移
19
moveUp()
调用函数,执行上移
20
moveRight()
调用函数,执行右移
第 57 关

扫雷 (Mine Field)

战术思路分析:生命值比例

英雄必须用身体引爆地雷,但生命值不能太低。当生命值低于**最大生命值的一半**时,必须撤退治疗。

关键:`hero.health` 和 `hero.maxHealth`

- **健康阈值:** `healingThreshold = hero.maxHealth / 2`
- **判断:** `if hero.health < healingThreshold:`
这是一种经典的**状态判断**,英雄根据自身状态决定行动(战斗或撤退)。

IF Health < MaxHealth / 2: Heal!

Python 程序解法

1
while True:
2
coin = hero.findNearestItem()
寻找硬币(地雷的位置)
3
healingThreshold = hero.maxHealth / 2
计算生命值阈值
4
# 检查你是否身受重伤。
5
if hero.health < healingThreshold:
如果当前生命值低于阈值
6
# 向左移动10米。
7
x = hero.pos.x
读取当前 X
8
y = hero.pos.y
读取当前 Y
9
hero.moveXY(x - 10, y)
向左移动 10 米
10
# 请求治疗。
11
hero.say("Can I get a heal?")
呼叫医生
12
# 否则,移动到下一枚硬币。
13
elif coin:
否则,如果找到了硬币
14
hero.moveXY(coin.pos.x, coin.pos.y)
继续前进(引爆地雷)
第 58 关

'Killdeer'操作 (Killdeer Operation)

战术思路分析:诱敌深入

食人魔只有在你看起来“受伤严重”时才会追击你。你需要利用这个机制,假装受伤,将他们引入陷阱(红色 X 标记处)。

shouldRun() 函数

我们用 `shouldRun()` 函数来判断英雄是否“看起来很弱”(生命值低于一半)。当函数返回 `True` 时,英雄就该跑了!

IF shouldRun(): moveXY(Trap)

Python 程序解法

1
def shouldRun():
定义逃跑决策函数
2
if hero.health < hero.maxHealth / 2:
如果血量低于一半
3
return True
返回 True (应该跑)
4
else:
否则
5
return False
返回 False (继续战斗)
6
7
while True:
8
# 只有当shouldRun()返回True时才移动到X.  True
9
if shouldRun():
如果函数返回 True
10
hero.moveXY(75, 37)
逃到陷阱位置
11
# 否则,攻击!
12
else:
否则
13
enemy = hero.findNearestEnemy()
寻找敌人
14
if enemy:
如果敌人存在
15
hero.attack(enemy)
战斗
第 59 关

医疗护理 (Medical Care)

战术思路分析:即时治疗

这次你没有诱敌深入的计划,只是纯粹的生死存亡。当血量低于一半时,必须立即去治疗师那里喊话治疗。

关键:`if / else` 结构

英雄只有两种选择:`if` (受伤去治疗) 或者 `else` (继续战斗)。

IF Health < Threshold: moveXY(Healer)

Python 程序解法

1
while True:
2
currentHealth = hero.health
读取当前生命值
3
healingThreshold = hero.maxHealth / 2
计算治疗阈值 (MaxHealth / 2)
4
if hero.health < healingThreshold:
如果生命值低于阈值
5
hero.moveXY(65, 46)
移动到治疗点
6
hero.say("Heal please!")
请求治疗
7
else:
否则 (健康时)
8
enemy = hero.findNearestEnemy()
寻找敌人
9
if enemy:
如果敌人存在
10
hero.attack(enemy)
攻击
第 60 关

概念挑战. 王之谷 (Valley of the Kings)

战术思路分析:生命值阈值

这次我们不是看英雄的血量,而是看**敌人的血量**。只有当骷髅的血量**高于**最大生命值的三分之一时,才攻击它。

公式:目标血量 > 阈值

攻击条件:`enemy.health > enemy.maxHealth / 3`
一旦低于这个阈值,敌人就太弱了,不值得攻击,我们跑开!

IF Enemy.Health > 1 / 3: Attack()

Python 程序解法

1
while True:
2
enemy = hero.findNearestEnemy()
寻找敌人
3
if enemy:
如果敌人存在
4
if enemy.health > enemy.maxHealth / 3:
如果敌人血量高于 MaxHealth 的 1/3
5
hero.attack(enemy)
攻击
6
else:
否则 (敌人太弱)
7
hero.moveXY(35, 16)
逃跑
第 61 关

组合挑战. 千岩谷 (Thousand Lashes)

战术思路分析:多重状态决策

这个终极挑战要求英雄同时处理三件事:
1. **生命值比例:** `health < maxHealth / 3` (决定是否呼叫治疗)
2. **物品位置:** `item.pos.x > hero.pos.x` (决定向右移动)
3. **物品位置:** `item.pos.y > hero.pos.y` (决定向上移动)

不相关 If 语句的顺序

**治疗呼叫**和**移动决策**是相互独立的,因此它们使用平级的 `if` 语句。移动决策中的 X 和 Y 也是独立判断的。

IF Low HP: Say("Heal!")
IF Item Right: X += 8
IF Item Up: Y += 8

Python 程序解法

1
while True:
2
if hero.health < hero.maxHealth / 3:
判断:如果血量低于 1/3
3
hero.say("治疗!")
呼叫治疗师
4
item = hero.findNearestItem()
寻找物品
5
if item:
如果物品存在
6
if item.pos.x > hero.pos.x:
如果物品在右边
7
hero.moveXY(hero.pos.x + 8, hero.pos.y)
向右移动 8 米
8
if item.pos.y > hero.pos.y:
如果物品在上方
9
hero.moveXY(hero.pos.x, hero.pos.y + 8)
向上移动 8 米
第 62 关

守时 (On Time)

战术思路分析:时间分配

英雄必须根据游戏时间切换任务:前 10 秒战斗,10 到 35 秒收集硬币,35 秒后再次战斗。

关键:`hero.time` 与 `elif`

- **`hero.time`:** 获取游戏开始后的秒数。
- **`elif`:** 确保时间段是互斥的。如果 `time < 10` 为 True,后面的 `elif` 即使条件满足也不会执行。

IF Time < 10: Fight
ELIF Time < 35: Collect
ELSE: Fight Again

Python 程序解法

1
while True:
2
# 如果是前十秒,攻击。
3
if hero.time < 10:
前 10 秒
4
enemy = hero.findNearestEnemy()
5
if enemy:
6
hero.attack(enemy)
攻击敌人
7
# 否则,如果是前35秒,收集硬币。
8
elif hero.time < 35:
否则,如果在 10 到 35 秒之间
9
coin = hero.findNearestItem()
10
if coin:
11
hero.moveXY(coin.pos.x, coin.pos.y)
收集硬币
12
# 35秒后,再次发起攻击!
13
else:
否则 (35 秒之后)
14
enemy = hero.findNearestEnemy()
15
if enemy:
16
hero.attack(enemy)
攻击敌人
第 63 关

沙漠十字 (Desert Cross)

战术思路分析:四象限攻击

食人魔从对角线(四个象限)进攻。你需要用布尔变量 (`isLeft`, `isAbove`) 来简化 `and` 运算的复杂逻辑,快速定位并放置陷阱。

布尔变量的应用

先将复杂的比较结果存入布尔变量:
`isLeft = hero.pos.x > enemy.pos.x`
然后组合它们:`if isLeft and isAbove:`

IF Left AND Above: Trap(TopLeft)

Python 程序解法

1
while True:
2
enemy = hero.findNearestEnemy()
3
if enemy:
4
# 左边:enemy.pos.x小于hero.pos.x
5
isLeft = hero.pos.x > enemy.pos.x
判断是否来自左边
6
# 上方:enemy.pos.y大于hero.pos.y
7
isAbove = hero.pos.y < enemy.pos.y
判断是否来自上方
8
# 右边:enemy.pos.x大于hero.pos.x
9
isRight = hero.pos.x < enemy.pos.x
判断是否来自右边
10
# 下方:enemy.pos.y小于hero.pos.y
11
isBelow = hero.pos.y > enemy.pos.y
判断是否来自下方
12
# 左上角
13
if isLeft and isAbove:
左上角:isLeft AND isAbove
14
hero.buildXY("fire-trap", 20, 51)
建造陷阱
15
# 右上角
16
if isRight and isAbove:
右上角:isRight AND isAbove
17
hero.buildXY("fire-trap", 60, 51)
建造陷阱
18
# 左下角
19
if isLeft and isBelow:
左下角:isLeft AND isBelow
20
hero.buildXY("fire-trap", 20, 17)
建造陷阱
21
# 右下角
22
if isRight and isBelow:
右下角:isRight AND isBelow
23
hero.buildXY("fire-trap", 60, 17)
建造陷阱
24
hero.moveXY(40, 34)
英雄回到中心
25
else:
否则
26
hero.moveXY(40, 34)
回到中心待命
第 64 关

囤积黄金 (Hoard)

战术思路分析:及时退出

收集到 25 金后,必须立即停止,否则你会被沙漠困住!你需要用 `break` 语句来强制退出无限循环。

关键:`break`

- `if totalGold >= 25:`
- break
`break` 会立即终止当前的 `while` 循环,程序跳转到循环后的第一条语句(即移动并报告)。

IF Goal Reached: break

Python 程序解法

1
totalGold = 0
初始化总金币数
2
while True:
3
coin = hero.findNearestItem()
寻找硬币
4
if coin:
如果硬币存在
5
hero.moveXY(coin.pos.x, coin.pos.y)
移动收集
6
totalGold += coin.value
累加金币价值
7
if totalGold >= 25:
如果达到 25 金的目标
8
break
立即中断循环
9
10
hero.moveXY(58, 33)
循环结束后,移动到 Naria
11
hero.say(totalGold)
报告总数
第 65 关

诱饵演习 (Decoy Drill)

战术思路分析:资源管理与建造

英雄需要收集金币,然后花费 25 金来建造一个诱饵 (`"decoy"`)。

关键:`hero.gold` 属性

- 检查资源:`if hero.gold >= 25:`
- 建造:`hero.buildXY("decoy", x, y)`
我们使用 `decoysBuilt` 计数器来跟踪已建造的数量,当达到 4 个时,使用 `break` 退出。

IF hero.gold >= 25: buildDecoy()

Python 程序解法

1
decoysBuilt = 0
诱饵计数器
2
while True:
3
coin = hero.findNearestItem()
寻找硬币
4
if coin:
如果硬币存在
5
hero.moveXY(coin.pos.x, coin.pos.y)
收集硬币
6
# 每个诱饵消费25金。
7
if hero.gold >= 25:
如果金钱达到 25
8
# 用buildXY建造一个"decoy"
9
hero.buildXY("decoy", hero.pos.x, hero.pos.y)
建造诱饵(花费 25 金)
10
# 为decoysBuilt计数值加1。
11
decoysBuilt += 1
计数 + 1
12
if decoysBuilt == 4:
如果建造了 4 个诱饵
13
# 建造了4个诱饵后跳出循环。
14
break
中断循环
15
hero.say("Done building decoys!")
报告建造完成
16
hero.moveXY(14, 36)
移动到报告点
17
hero.say(decoysBuilt)
报告总数
第 66 关

概念挑战. 贪婪保护 (Greedy Protection)

战术思路分析:见好就收

这个区域太危险了!收集到 99 金后,英雄必须立即使用 `break` 语句逃到南部的红色 X 标记处。

循环退出条件

使用 `hero.gold` 属性与 `maxGold` 目标进行比较:`if hero.gold >= maxGold:`
达到目标后,`break` 是唯一的出路。

IF Gold >= 99: break

Python 程序解法

1
maxGold = 99
定义目标金币数量
2
3
while True:
4
item = hero.findNearestItem()
寻找硬币
5
if item:
如果硬币存在
6
hero.moveXY(item.pos.x, item.pos.y)
移动收集
7
if hero.gold >= maxGold:
如果当前金币大于等于目标值
8
break
中断循环,逃跑
9
10
hero.moveXY(30, 8)
移动到红色 X 标记的安全区