HDU 1882 Strange Billboard(状态压缩+转置优化)
状态压缩,我们枚举第一行的所有状态,然后根据第一行去转变下面的行,枚举或者深搜直到最后最后一行,可以判断是不是所有的1都可以全部转换为0,记录所有的解,输出最小的一个就可以.
这里有一个很重要的优化,就是当n比m大的,转置这个矩阵,如果不加这个在G++的情况下会超时,C++900Ms多AC.代码及注释如下
#include<stdio.h>
#include<iostream>
#include<string.h>
#include<queue>
#include<algorithm>
using namespace std;
#define inf 0x3f3f3f
int row[],newrow[],n,m;
int dfs(int id,int prerow,int tot)
{
if(id == n)
{
if(prerow != )return inf;
else return tot;
}
int now = newrow[id];///这是当前行
for(int j = ; j < m; j++)
if(prerow & (<<j))///now(当前行)受prerow(前一行)的限制,只有prenow的这一列也是X的时候才可以反转
{
tot++;
now ^= <<j;
if(j > )now ^= <<(j-);
if(j < m-)now ^= <<(j+);
if(id+ < n)newrow[id+] ^= <<(j);///当前行的下一行
}
dfs(id+,now,tot);
}
int main()
{
char maps[][];
while(~scanf("%d%d",&n,&m))
{
if(n == && m == ) return ;
for(int i = ; i < n; i++)
scanf("%s",maps[i]);
if(n >= m)
{
for(int i = ; i < n; i++)
{
row[i] = ;
for(int j = ; j < m; j++)
if(maps[i][j] == 'X')
row[i] |= (<<j);
}
}
else///转置优化
{
for(int i = ; i < m; i++)
{
row[i] = ;
for(int j = ; j < n; j++)
if(maps[j][i] == 'X')
row[i] |= (<<j);
}
swap(n,m);
}
int ans = inf,tot;
for(int i=; i<(<<m); i++)///枚举第一行的所有状态
{
tot = ;
for(int j = ; j < n; j++)
newrow[j] = row[j];
for(int j=; (<<j)<=i; j++)
if(i & (<<j))///如果是X就反转,并且带动周围4个点,边界需要特判
{
tot++;
newrow[] ^= (<<j);
if(j > )newrow[] ^= (<<(j-));
if(j < m-)newrow[] ^= (<<(j+));
if(n > ) newrow[] ^= (<<j);
}
tot = dfs(,newrow[],tot);///开始搜索到最后一行
if(tot < ans)ans = tot;
}
if(ans == inf)printf("Damaged billboard.\n");
else printf("You have to tap %d tiles.\n",ans);
}
return ;
}
HDU 1882 Strange Billboard(状态压缩+转置优化)的更多相关文章
- hdu 1882 Strange Billboard(位运算+枚举)
http://acm.hdu.edu.cn/showproblem.php?pid=1882 感觉非常不错的一道题. 给一个n*m(1<=n,m<=16)的矩阵,每一个格子都有黑白两面,当 ...
- HDU 1882 Strange Billboard(位运算)
题目链接 题意 : 给你一个矩阵,有黑有白,翻转一个块可以让上下左右都翻转过来,问最少翻转多少次能让矩阵变为全白. 思路 : 我们从第一行开始枚举要翻转的状态,最多可以枚举到2的16次方,因为你只要第 ...
- hdu 4352 数位dp + 状态压缩
XHXJ's LIS Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total ...
- hdu 2825(ac自动机+状态压缩dp)
题意:容易理解... 分析:在做这道题之前我做了hdu 4057,都是同一种类型的题,因为题中给的模式串的个数最多只能为10个,所以我们就很容易想到用状态压缩来做,但是开始的时候我的代码超时了dp时我 ...
- [HDU 4336] Card Collector (状态压缩概率dp)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4336 题目大意:有n种卡片,需要吃零食收集,打开零食,出现第i种卡片的概率是p[i],也有可能不出现卡 ...
- HDU 4511 (AC自动机+状态压缩DP)
题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=4511 题目大意:从1走到N,中间可以选择性经过某些点,比如1->N,或1->2-> ...
- hdu 4856 Tunnels(bfs+状态压缩)
题目链接:hdu 4856 Tunnels 题目大意:给定一张图,图上有M个管道,管道给定入口和出口,单向,如今有人想要体验下这M个管道,问最短须要移动的距离,起点未定. 解题思路:首先用bfs处理出 ...
- HDU 3001 Travelling(状态压缩DP+三进制)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3001 题目大意:有n个城市,m条路,每条路都有一定的花费,可以从任意城市出发,每个城市不能经过两次以上 ...
- HDU 4628 Pieces(状态压缩+记忆化搜索)
http://acm.hdu.edu.cn/showproblem.php?pid=4628 题意:给个字符窜,每步都可以删除一个字符窜,问最少用多少步可以删除一个字符窜分析:状态压缩+记忆化搜索 ...
随机推荐
- JS获取网页中HTML元素的几种方法分析
getElementById getElementsByName getElementsByTagName 大概介绍 getElementById ,getElementsByName ,getEle ...
- PostMessage 向Windows窗口发送Alt组合键
PostMessage 向Windows窗口发送Alt组合键 关于向Windows窗口发送Alt组合键的问题,这个真是经典问题啊,在网上找了一下,问的人N多,方法差不多, 但就是没有很好解决问题. 之 ...
- Chapter 1 First Sight——28
"Which one is the boy with the reddish brown hair?" 那个红褐色头发的男孩是谁? I asked. I peeked at him ...
- 在 Visual Studio 2010 中创建 SharePoint 2010 事件接收器
Microsoft Visual Studio 2010 提供了一个可用于生成事件接收器的项目类型,事件接收器会在 Microsoft SharePoint 2010 网站上选择事件之前或之后执行操作 ...
- Mac 下格式化U盘
diskutil list 查看U盘盘符: lapommedeMacBook-Pro:~ lapomme$ diskutil list /dev/disk0 (internal, physical): ...
- ubuntu setup adb tool
sudo add-apt-repository ppa:nilarimogard/webupd8sudo apt-get updatesudo apt-get install android-tool ...
- UIView的基本属性及ANimation
frame属性:可以使用该属性改变尺寸和位置 相对于父视图bounds:改变尺寸 相对自身center:改变视图的位置alpha:改变视图的透明度backgroundColor:改变视图的背景cont ...
- iOS开发 GET、POST请求方法:NSURLSession篇
NSURLConnection,在iOS 9被宣布弃用,本文不使用NSURLConnection进行网络编程,有兴趣的童鞋可以参考: iOS开发 GET.POST请求方法(NSURLConnectio ...
- js里父页面与子页面的相互调用
一.在页面里用 open 打开的子页面: 1.子页面调用父页面的方法,包括子页面给父页面传值: window.opener.methodName(); window.opener.methodName ...
- group_concat()函数总结
group_concat(),手册上说明:该函数返回带有来自一个组的连接的非NULL值的字符串结果.比较抽象,难以理解. 通俗点理解,其实是这样的:group_concat()会计算哪些行属于同一组, ...