双向搜索,bfs,用pair来存储坐标方便很多
由于d要走两次,不太方便,所以我们直接bfs两次就好了
#include<bits/stdc++.h> using namespace std; typedef long long ll; typedef pair<int,int> PII; const int maxn = 1e6+6; int n, m; char a[1010][1010]; bool vis[2][1010][1010]; queue<PII> q[2]; int dir[8][2] = {{0,1},{1,0},{0,-1},{-1,0},{1,1},{1,-1},{-1,1},{-1,-1}}; int vans = 0; int nans = 0; bool bfs(int x) { int size = q[x].size(); //先记录队列长度 while(size --) //当队列不为0 { PII p = q[x].front(); //将队列第一个取下 q[x].pop(); //删除第一个 for(int k = 0; k < (x?4:8); k ++) //遍历第一个能到的点,然后插入对列 { int dx = p.first + dir[k][0]; int dy = p.second + dir[k][1]; if(dx>0&&dx<=n&&dy>0&&dy<=m&&a[dx][dy]!='#'&&!vis[x][dx][dy]) { if(vis[x^1][dx][dy] == 1) return 1;//这里的异或很奇妙 vis[x][dx][dy] = 1; q[x].push(make_pair(dx,dy)); } } } return 0; } int solve() { int res = 0; //记录走了几次 while(!q[0].empty()||!q[1].empty()) //只要两个队列有一个不空 { res ++; if(bfs(0)) return res; //如果走的位置,另一个已经走过了返回次数 if(bfs(1)) return res; if(bfs(1)) return res; } return -1; //如果最后都没有相遇返回-1 } int main() { cin >> n >> m; for(int i = 1; i <= n; i ++) { for(int j = 1; j <= m; j ++) { cin >> a[i][j]; if(a[i][j] == 'C') { q[0].push(make_pair(i,j)); //用pair类型存点 } if(a[i][j] == 'D') { q[1].push(make_pair(i,j));//用pair存 } } } int ans = solve(); if(ans == -1) printf("NO\n"); else { printf("YES\n"); printf("%d\n",ans); } return 0; }