POJ 1753 Flip Game (黑白棋) (状态压缩+BFS)
題目大意:有一個4*4的方格,每個方格中放一粒棋子,這個棋子一面是白色,一面是黑色。游戲規則為每次任選16顆中的一顆,把選中的這顆以及它四周的棋子一并反過來,當所有的棋子都是同一個顏色朝上時,游戲就完成了。現在給定一個初始狀態,要求輸出能夠完成游戲所需翻轉的最小次數,如果初始狀態已經達到要求輸出0。如果不可能完成游戲,輸出Impossible。
主要思想:
1.如果用一個4*4的數組存儲每一種狀態,不但存儲空間很大,而且在窮舉狀態時也不方便記錄。因為每一顆棋子都只有兩種狀態,所以可以用二進制0和1表示每一個棋子的狀態,則棋盤的狀態就可以用一個16位的整數唯一標識。而翻轉的操作也可以通過通過位操作來完成。顯然當棋盤狀態id為0(全白)或65535(全黑)時,游戲結束。
2.對于棋盤的每一個狀態,都有十六種操作,首先要判斷這十六種操作之后是否有完成的情況,如果沒有,則再對這十六種操作的結果分別再進行上述操作,顯然這里就要用到隊列來存儲了。而且在翻轉的過程中有可能會回到之前的某種狀態,而這種重復的狀態是不應該再次入隊的,所以維護isVis[i]數組來判斷id==i的狀態之前是否已經出現過,如果不是才將其入隊。如果游戲無法完成,狀態必定會形成循環,由于重復狀態不會再次入隊,所以最后的隊列一定會是空隊列。
3.由于0^1=1,1^1=0,所以翻轉的操作可以通過異或操作來完成,而翻轉的位置可以通過移位來確定。
# include <iostream># define N 65536using namespace std;int q[N*2];int front, rear, i, j, id = 0, tmp;bool vis[N]; //標記狀態是否出現過int step[N]; //記錄到達id==i時狀態翻轉所需次數char color; int main(void){for(i = 0; i < 4; i++)for(j = 0; j < 4; j++){cin >> color; //輸入初始狀態并轉換為idid <<= 1;if(color == 'b')id++;}if(id == 0 || id == 65535){cout << 0 << endl; //如果初始狀態滿足直接輸出return 0;}q[rear++] = id; //初始狀態id入隊vis[id] = true;step[id] = 0; //到達初始狀態所需次數置0while(front < rear) //隊列不為空繼續操作 {id = q[front++]; //隊頭元素出隊for(i = 0; i < 4; i++)for(j = 0; j < 4; j++){tmp = id; //需要遍歷隊頭元素的16種操作 每次還原tmpif(i == 0)tmp ^= 1 << (11-4*i-j); //翻轉的位置為15-(4*(i+1)+j)else if(i == 3)tmp ^= 1 << (19-4*i-j); //翻轉的位置為15-(4*(i-1)+j)else{tmp ^= 1 << (11-4*i-j);tmp ^= 1 << (19-4*i-j);}if(j == 0)tmp ^= 3 << (14-4*i-j); //翻轉的位置為15-(4*i+j)、15-(4*i+j+1)else if(j == 3)tmp ^= 3 << (15-4*i-j); //翻轉的位置為15-(4*i+j-1)、15-(4*i+j)else{tmp ^= 7 << (14-4*i-j); //翻轉的位置為15-(4*i+j-1)、15-(4*i+j)、15-(4*i+j+1) }if(tmp == 0 || tmp == 65535){cout << step[id]+1 << endl;return 0;}if(!vis[tmp]) //如果是新狀態 入隊 {q[rear++] = tmp;vis[tmp] = true;step[tmp] = step[id]+1; // 當前次數=到達隊頭元素所需次數+1 }}}cout << "Impossible" << endl;return 0;} View Code?
后記:
第一次做狀態壓縮的題,也是現學現賣,有些像位運算的公式什么的還是理解的不是很透徹,關于狀態壓縮的題還是需要再多做幾個。
?
轉載于:https://www.cnblogs.com/Silence-AC/p/3234199.html
總結
以上是生活随笔為你收集整理的POJ 1753 Flip Game (黑白棋) (状态压缩+BFS)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 新站收录记录
- 下一篇: 一步一步深入spring(1)--搭建和