题目:1915 -- Knight Moves (poj.org)
此题想要求掌握利用队列进行广度优先搜索的能力。另外也有一定的动态规划思想。
在做的过程中有几点需要注意(出错点):
1:如果初始点等于终止点则立刻跳出。
2:在BFS过程中要避免对已经搜索过的点进行二次搜索
3:由一个点搜索出的其他点位应该在步数上加1(类似于DP)
4:搜索出的点位不能越界
代码:
注:此代码还具备储存所有合法点位最小步数的功能
#include<iostream>
#include<queue>
#include<algorithm>
using namespace std;
typedef struct st {
int row;
int col;
}S;
int num[305][305];
int move1[8][2] = { 1,2,2,1,-1,2,-2,1,-1,-2,-2,-1,1,-2,2,-1 }; //八组偏移量
queue<S> s1;
int start_row, start_col, end_row, end_col;
int l;
int main() {
int n;
cin >> n;
while (n--) {
for (int i = 0; i < 305; i++)memset(num[i], -1, sizeof(num[0])); //初始化,使-1作为是否搜索过的条件
cin >> l >> start_row >> start_col >> end_row >> end_col;
//BFS
S s;
s.row = start_row, s.col = start_col;
num[s.row][s.col] = 0;
s1.push(s);
while (!s1.empty()) {
s.row = s1.front().row;
s.col = s1.front().col;
s1.pop();
if (start_row == end_row && start_col == end_col)break;
for (int i = 0; i < 8; i++) {
if (s.row + move1[i][0] >= 0 && s.row + move1[i][0] < l && s.col + move1[i][1]>=0 && s.col + move1[i][1] < l&&num[s.row + move1[i][0]][s.col + move1[i][1]]==-1) { //判断是否越界和是否已经搜索过
S ss;
ss.row = s.row + move1[i][0];
ss.col = s.col + move1[i][1];
num[ss.row][ss.col] = num[s.row][s.col] + 1;
s1.push(ss);
}
}
}
cout << num[end_row][end_col] << endl; //输出需要点位的步数
}
return 0;
}