CCF 201412-2 Z字形扫描
第一次的思路做错了嘤...
1 #include<iostream> 2 #include<cstring> 3 using namespace std; 4 int arr[505][505]; 5 bool visit[505][505]; 6 const int dr[] = {0,1,1,-1};//右0,左下1,下2,右上3 7 const int dc[] = {1,-1,0,1}; 8 int n; 9 bool inside(int x,int y) 10 { 11 return x>=0 && x<n && y>=0 && y<n; 12 } 13 void solve(int r,int c,int dir,int num) 14 { 15 if(r>0 || c>0) cout<<" "; 16 cout<<arr[r][c]; 17 visit[r][c] = false; 18 if(num == n*n) return; 19 if(r == 0 && inside(r+dr[1],c+dc[1]) && visit[r+dr[1]][c+dc[1]]) 20 {//在第一行而且存在左下,左下没有读取 21 solve(r+dr[1],c+dc[1],1,num+1); 22 } 23 else if(r == 0 && c!=n-1 && !inside(r+dr[1],c+dc[1]) || r == 0 && c!=n-1 && !visit[r+dr[1]][c+dc[1]]) 24 {///在第一行,没有左下或者是左下已经读取,则向右 25 if(inside(r+dr[0],c+dc[0])) 26 solve(r+dr[0],c+dc[0],0,num+1); 27 } 28 else if(c == 0 && r != 0 && visit[r+dr[3]][c+dc[3]]){ 29 ///在第一列,右上没有读取,则右上 30 if(inside(r+dr[3],c+dc[3])) 31 solve(r+dr[3],c+dc[3],3,num+1); 32 } 33 else if(c == 0 && r != n-1 && r != 0 && !visit[r+dr[3]][c+dc[3]]){ 34 ///在第一列,右上已经读取则向下 35 if(inside(r+dr[2],c+dc[2])) 36 solve(r+dr[2],c+dc[2],2,num+1); 37 } 38 else if(r == n-1 && visit[r+dr[3]][c+dc[3]]) { 39 ///在最后一行,右上没有读取,则右上 40 if(inside(r+dr[3],c+dc[3])) 41 solve(r+dr[3],c+dc[3],3,num+1); 42 } 43 else if(r == n-1 && !visit[r+dr[3]][c+dc[3]]){ 44 ///在最后一行,右上已经读取,则向右 45 if(inside(r+dr[0],c+dc[0])) 46 solve(r+dr[0],c+dc[0],0,num+1); 47 } 48 else if(c==n-1 && visit[r+dr[1]][c+dc[1]]){ 49 ///在最右一列,如果左下没有读取则向左下 50 if(inside(r+dr[1],c+dc[1])) 51 solve(r+dr[1],c+dc[1],1,num+1); 52 } 53 else if(c==n-1 && !visit[r+dr[1]][c+dc[1]]){ 54 ///在最右一列,如果左下已经读取则向下 55 if(inside(r+dr[2],c+dc[2])) 56 solve(r+dr[2],c+dc[2],2,num+1); 57 }else{ 58 ///继续相当前方向 前进 59 if(inside(r+dr[dir],c+dc[dir])) 60 solve(r+dr[dir],c+dc[dir],dir,num+1); 61 } 62 } 63 64 int main() 65 { 66 while(cin>>n) 67 { 68 memset(visit,true,sizeof(visit)); 69 ///输入 70 for(int i=0;i<n;i++) 71 for(int j=0;j<n;j++) 72 { 73 cin>>arr[i][j]; 74 } 75 solve(0,0,0,1); 76 cout<<endl; 77 } 78 79 return 0; 80 }
1 #include<iostream> 2 using namespace std; 3 int arr[505][505]; 4 int n; 5 struct node{ 6 int x,y; 7 }; 8 void show(node c) 9 { 10 cout<<arr[c.x][c.y]<<" "; 11 } 12 bool inside(int x,int y) 13 { 14 return x>=0 && x<n && y>=0 && y<n; 15 } 16 int main() 17 { 18 cin>>n; 19 for(int i=0;i<n;i++) 20 for(int j=0;j<n;j++) 21 { 22 cin>>arr[i][j]; 23 } 24 node current = {0,0}; 25 show(current); 26 while(true) 27 { 28 if(current.x ==n-1 && current.y == n-1)///到达最后一个结点 29 { 30 break; 31 } 32 ///将每次回到第一行或最后一列,看作一个循环 33 ///1.在第一行或是最后一列,有两种选择,有右边向右,否则向下 34 if(inside(current.x,current.y+1)) { 35 ///可以向右 36 current.y++; 37 show(current); 38 }else{ 39 ///不能向右,则向下 40 current.x++;show(current); 41 } 42 ///2.继续向左下 43 while(inside(current.x+1,current.y-1)) 44 { 45 current.x++;current.y--; 46 show(current); 47 } 48 ///3.在第一列或是最后一行,如果有下边就向下,否则向右 49 if(inside(current.x+1,current.y)) { 50 ///向下 51 current.x++;show(current); 52 }else{ 53 ///向右 54 current.y++;show(current); 55 } 56 ///4.向右上 57 while(inside(current.x-1,current.y+1)){ 58 current.x--;current.y++; 59 show(current); 60 } 61 } 62 63 return 0; 64 }