

首先学习了一下别人的代码,用的深优,确实自己好久不接触这一部分代码了,导致自己根本没想递归的那一方面,dfs的方式可能有些弊端,但是代码相对来讲更容易实现一些。
另外就是if的判断规则,以前这边有点模糊,有点印象,但是不太确定,这次试验了一下,果然是从左向右依次判断。—— 在 “||” 条件下,发现一个满足即可走if里,后面的条件不再判断;
#include <iostream>
#include<iomanip>
#include<math.h>
using namespace std;
void dfs(int **a,int m,int n,int al,int bl) {
if (m < 0 || n < 0 || m >= al || n >= bl || a[m][n] == -1) {
//这里a[m][n]要放在最后,
//学到了,放在前面的话就有可能数组越界的错误
//(if的判断顺序)
return;
}
if (m == 0 && n == 0)cout << a[m][n];
else cout << " " << a[m][n];
a[m][n] = -1;
dfs(a, m + 1, n, al, bl);
dfs(a, m, n + 1, al, bl);
dfs(a, m - 1, n, al, bl);
dfs(a, m, n - 1, al, bl);
}
int main() {
int a, b;
while (cin >> a >> b) {
int** array = new int* [a];
for (int i = 0; i < a; i++) {
array[i] = new int [b];
}
for (int i = 0; i < a; i++) {
for (int j = 0; j < b; j++) {
cin >> array[i][j];
}
}
dfs(array, 0, 0, a, b);
cout << endl;
}
return 0;
}
但是用这种方式ac不了,可能是数据量过大,导致爆栈。所以只能细分逻辑去写循环了。
#include <iostream>
#include<iomanip>
#include<math.h>
using namespace std;
int main() {
int m, n;
while (cin >> m >> n) {
int** a = new int* [m];
for (int i = 0; i < m; i++) {
a[i] = new int[n];
}
for (int i = 0; i < m; i++) {
for (int j = 0; j < n; j++) {
cin >> a[i][j];
}
}
int i = 1, j = 0;
int num = m * n - 1;
cout << a[0][0]; // DHU的oj风格 最后一个元素后没有空格
while (num) {
//cout << i << " " << j << endl;
int flag = 1;
//往下走
for (; i < m; i++) {
//cout << "下" << endl;
if (a[i][j] != -1) {
cout << " " << a[i][j];
a[i][j] = -1;
num--;
}
else {
i--;
flag = 0;
break;
}
}
if (num == 0)break;
//右转准备
if (flag == 1)i--;
if (j < n - 1) j++;
flag = 1;
//往右走
for (; j < n; j++) {
if (a[i][j] != -1) {
cout << " " << a[i][j];
a[i][j] = -1;
num--;
}
else {
j--;
flag = 0;
break;
}
}
if (num == 0)break;
//上转准备
if (flag == 1)j--;
if (i > 0 && i < m)i--;
//往上走
flag = 1;
for (; i >= 0 && i < m; i--) {
if (a[i][j] != -1) {
cout << " " << a[i][j];
a[i][j] = -1;
num--;
}
else {
i++;
flag = 0;
break;
}
}
if (num==0)break;
if (flag == 1)i++;
if (j > 0) j--;
flag = 1;
for (; j > 0; j--) {
if (a[i][j] != -1) {
cout << " " << a[i][j];
a[i][j] = -1;
num--;
}
else {
j++;
flag = 0;
break;
}
}
if (num == 0)break;
//下一次下转准备
if (flag == 1) j++;
if (i < m - 1)i++;
}
cout << endl;
}
return 0;
}
一开始在写的时候判断逻辑偷懒了,每个if的条件写的不够全面,所以到后面调试的时候只好在每次转向之前先判断是否break(跳出整体循环)才AC掉。