题目链接:https://www.luogu.org/problemnew/show/P1126
题意:
给定一个n*m的方格,机器人推着直径是1.6的球在格子的线上运动。
每一秒钟可以向左转,向右转或者直走1步2步或是3步。
现在给定一个起点和开始的朝向,问走到终点至少要多少时间。
思路:
真是一道狗屎坑题。题目给出的是格点,而机器人是在交点上运动的。
盗用一下洛谷@雒仁韬的图。题目给出的障碍物其实是橙色的四个点中的右下角的这个。
而且由于球的直径,最外围边界并不能走到。如果正确理解了题意的话应该就没问题了。
由于有方向,所以用三维数组来存某点是否被访问。
1 #include<stdio.h> 2 #include<stdlib.h> 3 #include<map> 4 #include<set> 5 #include<iostream> 6 #include<cstring> 7 #include<algorithm> 8 #include<vector> 9 #include<queue> 10 11 using namespace std; 12 13 int n, m; 14 int mat[55][55]; 15 //0E, 1S, 2W, 3N 16 int dx[4][3] = {{0, 0, 0}, {1, 2, 3}, {0, 0, 0}, {-1, -2, -3}}; 17 int dy[4][3] = {{1, 2, 3}, {0, 0, 0}, {-1, -2, -3}, {0, 0, 0}}; 18 bool vis[55][55][5]; 19 struct node{ 20 int x, y; 21 int dir; 22 int t; 23 }st, ed; 24 25 int getdir(char c) 26 { 27 if(c == 'E')return 0; 28 if(c == 'S')return 1; 29 if(c == 'W')return 2; 30 if(c == 'N')return 3; 31 } 32 33 bool check(int i, int j) 34 { 35 return (i >= 1 && i < n && j >= 1 && j < m); 36 } 37 38 int main() 39 { 40 scanf("%d%d", &n, &m); 41 for(int i = 1; i <= n; i++){ 42 for(int j = 1; j <= m; j++){ 43 scanf("%d", &mat[i][j]); 44 if(mat[i][j]){ 45 mat[i - 1][j] = 1; 46 mat[i][j - 1] = 1; 47 mat[i - 1][j - 1] = 1; 48 } 49 } 50 } 51 52 scanf("%d%d%d%d", &st.x, &st.y, &ed.x, &ed.y); 53 char dir; 54 //st.x--;st.y--;ed.x--;ed.y--; 55 getchar(); 56 scanf("%c", &dir); 57 st.dir = getdir(dir); 58 st.t = 0; 59 60 queue<node>que; 61 que.push(st); 62 vis[st.x][st.y][st.dir] = true; 63 int ans = -1; 64 while(!que.empty()){ 65 node now = que.front();que.pop(); 66 //cout<<endl<<now.x<<" "<<now.y<<" "<<now.t<<endl; 67 if(now.x == ed.x && now.y == ed.y){ 68 ans = now.t; 69 break; 70 } 71 node to; 72 to.x = now.x;to.y = now.y;to.t = now.t + 1; 73 to.dir = (now.dir + 1) % 4; 74 if(!vis[to.x][to.y][to.dir]){ 75 vis[to.x][to.y][to.dir] = true; 76 que.push(to); 77 } 78 to.dir = (now.dir - 1 + 4) % 4; 79 if(!vis[to.x][to.y][to.dir]){ 80 vis[to.x][to.y][to.dir] = true; 81 que.push(to); 82 } 83 84 to.dir = now.dir; 85 for(int i = 0; i < 3; i++){ 86 to.x = now.x + dx[to.dir][i]; 87 to.y = now.y + dy[to.dir][i]; 88 if(mat[to.x][to.y])break; 89 if(check(to.x, to.y) && !vis[to.x][to.y][to.dir]){ 90 vis[to.x][to.y][to.dir] = true; 91 que.push(to); 92 //cout<<to.x<<" "<<to.y<<" "<<to.t<<endl; 93 } 94 } 95 } 96 97 cout<<ans<<endl; 98 99 return 0; 100 }