第三讲 搜索与图论


1.DFS

AcWing 842. 排列数字

https://www.acwing.com/activity/content/problem/content/905/

点击查看代码
#include 
using namespace std;

const int N = 100010;
int n;
bool vis[N];
int cnt[10]; //输出字符
void dfs(int idx){
	if(idx == n+1){
		for(int i = 1; i <= n; i++){
			cout << cnt[i] << " ";
		}
		cout << endl;
	}
	for(int i = 1; i <= n; i++){
		if(!vis[i]){
			vis[i] = 1;
			cnt[idx] = i;
			dfs(idx+1);
			vis[i] = 0;
		}
	}
}

int main(){
	cin >> n;
	dfs(1); //从第一个数字开始dfs
	return 0;
}

AcWing 843. n-皇后问题

https://www.acwing.com/problem/content/845/

点击查看代码
#include 
using namespace std;
// n皇后,每个皇后在不同行,不同列,不在一个斜线上
// 一共摆n个皇后,那么每行都要摆一个,且只能摆一个
int n; // 1~9
char g[10][10];

bool isok(int r,int c){
	for(int i = 1; i <= r-1; i++){
		for(int j = 1; j <= n; j++){
			if(g[i][j] == 'Q'){
				if(c == j) return false; //同列
				if((c-j)*(c-j) == (r-i)*(r-i)) return false; //同一斜线上
			}
		}
	}
	return true;
}

void dfs(int row){
	if(row == n+1){
		// output
		for(int i = 1; i <= n; i++){
			for(int j = 1; j <= n; j++){
				if(g[i][j] != 'Q') cout << ".";
				else cout << g[i][j]; 
			}
			cout << endl;
		}
		cout << endl;
	}
	// 枚举列的位置
	for(int i = 1; i <= n; i++){
		if(isok(row,i)){
			g[row][i] = 'Q';
			dfs(row+1);
			g[row][i] = ' ';
		}
	}
}

int main(){

	cin >> n;
	dfs(1); //从第一行开始

	return 0;
}

BFS

Acwing844 走迷宫

https://www.acwing.com/activity/content/problem/content/907/

点击查看代码
#include 
#include 
#include 
using namespace std;

const int N = 1010;
int g[N][N];
bool vis[N][N];
int n,m; // n*m的二维数组
int dir[4][2] = {1,0,0,1,-1,0,0,-1};
queue,int> > q; // (x,y),step 

bool isok(int x,int y){
	if(x < 1 || x > n || y < 1 || y > m) return false;
	return true;
}

int bfs(){
	
	q.push(make_pair(make_pair(1,1),0));
	vis[1][1] = 1;
	while(!q.empty()){
		int x = q.front().first.first;
		int y = q.front().first.second;
		int step = q.front().second;
		if(x ==  n && y == m){
			return step;
		}
		q.pop();
		for(int i = 0; i < 4; i++){
			int xx = x + dir[i][0];
			int yy = y + dir[i][1];
			if(g[xx][yy] == 0 && !vis[xx][yy] && isok(xx,yy)) {
				vis[xx][yy] = 1;
				q.push(make_pair(make_pair(xx,yy),step+1));
			}
		}
	}
	return -1;

}


int main(){
	cin >> n >> m;
	for(int i = 1; i <= n; i++){
		for(int j = 1; j <= m; j++){
			cin >> g[i][j];
		}
	}

	cout << bfs() << endl;

	return 0;
}