解题思路:
先找到坦克的起始点,用变量记录下来。用广搜 -dfs的方式解决。
题的目标:最少移动步数数 有则输出无则输出-1
dfs的技巧:
先开栈避免因数据规模太大递归次数太多而出现爆栈的情况,分不清是记忆化搜索还是不是记忆化搜索那就直接写上lru_cache(maxsize=None)
分析:
坦克只能是所在位置与下一个位置不同时才能行走所以要判断Map[xx][yy]是否与Map[x][y]相等,相等要跳过,不相等给走过的位置打商标机然后dfs(xx,yy,depth+1) 最后再清除标记。
坦克可以上下左右移动所以要设置一个移动数组dirt = [[0, 1], [0, -1], [1, 0], [-1, 0]]遍历数组代表了向四周移动,注意要判断边界
注意事项:
标记数组一定要用列表推导式写,不然会出错,具体原因我也不知道
参考代码:
from functools import lru_cache
import sys
#明天来了给走过的路径打标记,回去睡觉
sys.setrecursionlimit(1000000)
@lru_cache(maxsize=None)
def dfs(x, y, depth):
global ans
if depth > ans:
return
if x == x2 and y == y2:
ans = min(ans, depth)
return
for i in range(4):
xx = x + dirt[i][0]
yy = y + dirt[i][1]
if 0 <= xx < n and 0 <= yy < n:
if vis[xx][yy]==True:
continue
if Map[xx][yy] != Map[x][y]:
vis[xx][yy]=True
dfs(xx, yy, depth + 1)
vis[xx][yy]=False
n = int(input())
Map = []
for i in range(n):
Map.append(list(input().split()))
x1, y1, x2, y2 = 0, 0, 0, 0
for i in range(n):
for j in range(n):
if Map[i][j] == "A":
x1 = i
y1 = j
if Map[i][j] == 'B':
x2 = i
y2 = j
dirt = [[0, 1], [0, -1], [1, 0], [-1, 0]]
vis=[[False]*n for _ in range(n)]
#bi标记数组一定要用推导式写,不然会出现错误
#vis=[[False]*n]*n
ans = 10000000000
dfs(x1,y2,0)
if ans==10000000000:
ans=-1
else:
ans
print(ans)
0.0分
0 人评分
C语言训练-最大数问题 (C语言代码).........关于-1浏览:744 |
母牛的故事 (C语言代码)浏览:668 |
C语言训练-求s=a+aa+aaa+aaaa+aa...a的值 (C++代码)(手动优化一下计算)浏览:1282 |
C二级辅导-统计字符 (C语言代码)浏览:503 |
C语言训练-求素数问题 (C语言代码)浏览:1452 |
简单的a+b (C语言代码)浏览:670 |
C语言程序设计教程(第三版)课后习题10.5 (C语言代码)浏览:546 |
简单的a+b (C语言代码)浏览:521 |
WU-字符串比较 (C++代码)浏览:756 |
C语言程序设计教程(第三版)课后习题1.6 (C语言代码)浏览:655 |