Fliptile POJ - 3279(状态压缩)

题意:给你一个n * m的矩阵,元素为0/1, 求把所有的元素变成0所需要的最少操作。(每对一个格子操作,该十字格的元素反转)

分析:一看数据量 <= 15, 就有点状态压缩的感jio。从小到大枚举第一行的操作,因为第一行的操作决定了后面所有的操作,所以最后判断对于第一行的操作是不是符合题意即可。

代码:

 1 #include <iostream>
 2 #include <cstring>
 3 #include <algorithm>
 4 #include <map>
 5 using namespace std;
 6 const int maxn = 20;
 7 int now;
 8 int g[maxn][maxn];
 9 int cnt[maxn][maxn];
10 int res[(1 << 15) + 10][maxn][maxn];
11
12 int main()
13 {
14     int n, m; cin >> n >> m;
15     for (int i = 1; i <= n; i++)
16         for (int j = 1; j <= m; j++)
17             cin >> g[i][j];
18     int minn = 1e9;
19     for (now = 0; now < (1 << m); now++)
20     {
21         int tmp = now;
22         int ope = 0;
23         memset(cnt, 0, sizeof(cnt));
24         for (int i = m; i >= 1; i--)
25         {
26             if (tmp & 1)
27             {
28                 ope++;
29                 cnt[1][i]++, cnt[2][i]++;
30                 if (i >= 2) cnt[1][i - 1]++;
31                 if (i <= m - 1) cnt[1][i + 1]++;
32                 res[now][1][i]++;
33             }
34             tmp >>= 1;
35         }
36         for(int i = 2; i <= n; i++)
37             for (int j = 1; j <= m; j++)
38             {
39                 if ((g[i - 1][j] + cnt[i - 1][j]) & 1)
40                 {
41                     ope++;
42                     cnt[i][j]++, cnt[i - 1][j]++, cnt[i + 1][j]++;
43                     if (j >= 2) cnt[i][j - 1]++;
44                     if (j <= m - 1) cnt[i][j + 1]++;
45                     res[now][i][j]++;
46                 }
47             }
48         int flag = 0;
49         for(int i = 1; i <= m; i++)
50             if ((g[n][i] + cnt[n][i]) & 1)
51             {
52                 flag = 1;
53                 break;
54             }
55         if (!flag)
56             res[now][0][0] = ope, minn = min(minn, ope);
57         else res[now][0][0] = -1;
58     }
59     for(int i = 0; i < (1 << 15); i++)
60         if (res[i][0][0] == minn)
61         {
62             for (int j = 1; j <= n; j++)
63                 for (int k = 1; k <= m; k++)
64                     printf("%d%c", res[i][j][k], k == m ? ‘\n‘ : ‘ ‘);
65             return 0;
66         }
67     printf("IMPOSSIBLE");
68 }

原文地址:https://www.cnblogs.com/liuwenhan/p/11665879.html

时间: 2024-09-30 08:30:58

Fliptile POJ - 3279(状态压缩)的相关文章

Mondriaan&#39;s Dream(POJ 2411状态压缩dp)

题意:用1*2的方格填充m*n的方格不能重叠,问有多少种填充方法 分析:dp[i][j]表示i行状态为j时的方案数,对于j,0表示该列竖放(影响下一行的该列),1表示横放成功(影响下一列)或上一列竖放成功.状态转移时,枚举每一行可能的状态上一行取反得下一行能放的状态. #include <map> #include <set> #include <list> #include <cmath> #include <queue> #include &

POJ 3311 状态压缩DP

题意:求从0点走到所有点又走回来的最短距离 该题又很多做法,我用的是弗洛伊德+状态压缩 先遍历所有点,求出两点间最短的距离,而后用状态压缩表示该点是否走过,(1<<n)-1则表示所有点都走过. 附AC代码 #include<stdio.h> #include<string.h> int map[12][12]; int dp[(1<<12)+1][12]; int min1(int a,int b) { if(a<b) return a; return

poj 1324 状态压缩+bfs

http://poj.org/problem?id=1324 Holedox Moving Time Limit: 5000MS   Memory Limit: 65536K Total Submissions: 17042   Accepted: 4065 Description During winter, the most hungry and severe time, Holedox sleeps in its lair. When spring comes, Holedox wakes

POJ 2411 状态压缩递,覆盖方案数

无非就是横着放与竖着放,状态中用1表示覆盖,0表示未覆盖. 1 #include <iostream> 2 #include <vector> 3 #include <algorithm> 4 #include <string> 5 #include <string.h> 6 #include <stdio.h> 7 #include <queue> 8 #include <stack> 9 #include

poj 3250 状态压缩dp入门

Corn Fields Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 7798   Accepted: 4159 Description Farmer John has purchased a lush new rectangular pasture composed of M by N (1 ≤ M ≤ 12; 1 ≤ N ≤ 12) square parcels. He wants to grow some yumm

Enum:Fliptile(POJ 3279)

Fliptile 题目大意:农夫想要测牛的智商,于是他把牛带到一个黑白格子的地,专门来踩格子看他们能不能把格子踩称全白 这一题其实就是一个枚举题,只是我们只用枚举第一行就可以了,因为这一题有点像开关一样,一个翻了,另一个就要跟着一起翻,第一行会影响下面所有行,而且影响情况只有一种,所以枚举完了以后我们不断模拟就可以了 1 #include <iostream> 2 #include <functional> 3 #include <algorithm> 4 5 usin

poj 1185 状态压缩

炮兵阵地 Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 27926   Accepted: 10805 Description 司令部的将军们打算在N*M的网格地图上部署他们的炮兵部队.一个N*M的地图由N行M列组成,地图的每一格可能是山地(用"H" 表示),也可能是平原(用"P"表示),如下图.在每一格平原地形上最多可以布置一支炮兵部队(山地上不能够部署炮兵部队):一支炮兵部队在地图上的攻

poj 3254 状态压缩

Corn Fields Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 15285   Accepted: 8033 Description Farmer John has purchased a lush new rectangular pasture composed of M by N (1 ≤ M ≤ 12; 1 ≤ N ≤ 12) square parcels. He wants to grow some yum

poj 2688 状态压缩dp解tsp

题意: 裸的tsp. 分析: 用bfs求出任意两点之间的距离后可以暴搜也可以用next_permutation水,但效率肯定不如状压dp.dp[s][u]表示从0出发访问过s集合中的点,目前在点u走过的最短路程. 代码: //poj 2688 //sep9 #include <iostream> #include <queue> using namespace std; const int maxW=32; const int maxN=12; int dx[4]={-1,1,0,