首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> C++ >> 關於C++

POJ 3279 - 矩陣翻轉遊戲(Lights Out 種)搜索解法

     編輯:關於C++

給定 15x15 以內的 0-1 矩陣,每次操作翻轉一個格子及其上下左右四鄰域。求最少操作次數使全矩陣變為 0。若有多解,需輸出字典序最小的方案(本題實測不嚴格檢查字典序)。

核心觀察:第一行決定一切

操作具有可交換性且兩次抵消。對於第 i (i>1) 行的格子 (i, j),其最終狀態僅受 (i-1, j) 的操作影響(因為只有上方操作能翻轉它而不影響已確定的上方行)。因此:

  1. 枚舉第一行的所有 2^m 種操作組合(m 列)。
  2. 對於第 2 到 n 行:若上一行第 j 列為 1,則當前行第 j 列必須操作(翻轉它)。
  3. 檢查最後一行是否全 0。若是,記錄總操作數,更新最小值。

複雜度 O(2^m * n * m),m <= 15 完全可行。

代碼關鍵邏輯

int cnt = (1 << m) - 1;
for (int w = 0; w <= cnt; w++) { // 枚舉第一行狀態
    memcpy(b, a, sizeof(a));
    memset(vis, 0, sizeof(vis));
    int sum = 0;
    // 處理第一行
    for (int j = 0; j < m; j++) if (w & (1<

總結

經典的「首行枚舉 + 逐行確定」策略,利用操作的局部性和可逆性將指數級搜索壓縮為 O(2^m)。類似問題包括 POJ 1222、HDU 1561 等。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved