链接:登录—专业IT笔试面试备考平台_牛客网
来源:牛客网
题目描述
给一个 n×mn\times mn×m 矩阵迷宫, 第 iii 行第 jjj 列的值为 ci,jc_{i,j}ci,j ,LHLHLH 在迷宫中迷路了,他需要你的帮助。
LHLHLH 当前在 (1,1)(1,1)(1,1) 的位置,出口在 (n,m)(n,m)(n,m),这个迷宫有一个计数器,只有当计数器的值模 (p−1)(p-1)(p−1) 的余数为 000 时迷宫出口才会开门(出口没有开门意味着即使在 (n,m)(n,m)(n,m) 的位置也不能逃出去)。
LHLHLH 每一秒会向迷宫的上下左右四个方向走一步(不可以不走),并且不能走出迷宫的边界,假设 LHLHLH 从 (i,j)(i,j)(i,j) 走到了 (i′,j′)(i',j')(i′,j′),然后计数器将会加上 ci′,j′c_{i',j'}ci′,j′。
特别的,计数器初始是 c1,1c_{1,1}c1,1。
ci,j=ai,j×p2bi,jc_{i,j}=a_{i,j}\times p^{2^{b_{i,j}}}ci,j=ai,j×p2bi,j。
现在 LHLHLH 问你,他最快需要多久才可以走出迷宫。
输入描述:
第一行输出三个整数 n,m,p(1≤n,m≤10,2≤p≤104)n,m,p(1\le n,m\le 10,2\le p\le 10^4)n,m,p(1≤n,m≤10,2≤p≤104)。 接下来输入一个 nnn 行 mmm 列的矩阵 ai,ja_{i,j}ai,j。 接下来输入一个 nnn 行 mmm 列的矩阵 bi,jb_{i,j}bi,j。 0≤ai,bi≤1060\le a_i,b_i\le 10^60≤ai,bi≤106。
输出描述:
输出一个整数,表示满足条件的最短路径长度。 假如不存在一条路径满足条件,输出 −1。
输入:
3 3 10
1 2 3
0 1 4
0 0 0
1 0 0
0 0 1
0 1 0
输出:
6
链接:登录—专业IT笔试面试备考平台_牛客网
来源:牛客网
C=⎣⎡1000020100304000⎦⎤。
第一秒,从 (1,1)(1,1)(1,1) 走到 (1,2)(1,2)(1,2),计数器的值为 120120120。
第二秒,从 (1,2)(1,2)(1,2) 走到 (1,3)(1,3)(1,3),计数器的值为 150150150。
第三秒,从 (1,3)(1,3)(1,3) 走到 (1,2)(1,2)(1,2),计数器的值为 170170170。
第四秒,从 (1,2)(1,2)(1,2) 走到 (2,2)(2,2)(2,2),计数器的值为 180180180。
第五秒,从 (2,2)(2,2)(2,2) 走到 (3,2)(3,2)(3,2),计数器的值为 180180180。
第六秒,从 (3,2)(3,2)(3,2) 走到 (3,3)(3,3)(3,3),计数器的值为 180180180,是 999 的倍数,逃出迷宫。
思路:
一看到路径问题,还是最短路径/时间,首先想到了bfs。
暴力:
由于可以重复走,st[i][j]好像不能用了,不需要只标记一次就行,但是会导致来回走,所以想到了可以多加一维来表示余数k,这样可以标记在走到当前位置时,余数为k的最短路径,如果已经走过那么路径肯定会比之前的要长。
表示为:dis[i][j][k] st[i][j][k]
优化:
没有想到原来c[i][j]就是a[i][j],起初在写的时候直接暴力把c求出来在存起来,非常浪费时间,后来又只把c对(p-1)的余数存起来,惊人发现居然等于a数组,于是可以进一步简化计算。
BUT!
不知道为什么我的python代码还是会超时,希望有缘人可以帮忙指正,感觉自己的思路已经梳理通了。T-T
from collections import deque n, m, p = map(int, input().split()) dx = [0, 1, 0, -1] dy = [1, 0, -1, 0] a = [] b = [] dis = [[[float('inf')] * 10010 for _ in range(m)] for _ in range(n)] st = [[[0] * 10010 for _ in range(m)] for _ in range(n)] end = (n - 1, m - 1) # 读入矩阵 a 和 b for i in range(n): row = list(map(int, input().split())) a.append(row) for i in range(n): row = list(map(int, input().split())) b.append(row) q = deque() q.append((0, 0, a[0][0] % p)) dis[0][0][a[0][0] % (p - 1)] = 0 st[0][0][a[0][0] % (p - 1)] = 1 def bfs(): while q: i, j, k = q.popleft() for d in range(4): x = i + dx[d] y = j + dy[d] if 0 <= x < n and 0 <= y < m: new_res = (k + a[x][y]) % (p - 1) if st[x][y][new_res] == 1: continue dis[x][y][new_res] = dis[i][j][k] + 1 st[x][y][new_res] = 1 q.append((x, y, new_res)) if dis[n - 1][m - 1][0] != float('inf'): return dis[n - 1][m - 1][0] else: return -1 res = bfs() print(res)