复习面经之n皇后问题
八皇后问题
经典八皇后问题大概是说8*8的国际象棋棋盘上,如果同行或者同列或者同对角线上存在多个皇后 则它们会互相攻击,求在棋盘上和平的摆上八个皇后的方案数。
推广至N皇后
这里以前一直是使用暴力搜索解决的
然后最近想到可以用状态压缩来解决,就有了这篇文章
使用状态压缩可以通过位运算减少遍历数组所带来的消耗,理解起来也更简洁
首先在处理状态压缩需要用到位运算的知识,这里不多概述,只会解释所用到的。
上代码
void dfs(int Col, int mainDiag, int contDiag) {
if (Col == (1 << n) - 1) {
ans++;
return;
}
//求当前行可以摆放皇后的列
//三个参数中各位上的1表示不可摆放 先或再取反则表示整个棋盘上1为可以摆放的位置
//前面那一串表示所有位置都可以摆放
int colCan = (((1 << n) - 1))&(~(Col|mainDiag|contDiag));
//从后往前遍历所有可摆位置
while (colCan) {
//试探在col列上摆放上皇后 col为最右边的可拜访位置
//这里的式子是lowbit的公式 计算最低位的1的位置
int col = (colCan & (~(colCan)+1));
//将摆完位置置0
colCan &= (~col);
//三个参数中新增的1的位置表示对下一行的影响
//col为对当前列 后面两个都是记录对角线所以下一行是当前列的两边不可摆放
dfs(Col | col, (mainDiag | col) >> 1, (contDiag | col) << 1);
}
}