【BZOJ 2669】 2669: [cqoi2012]局部极小值 (状压DP+容斥原理)
2669: [cqoi2012]局部极小值
Time Limit: 3 Sec Memory Limit: 128 MB
Submit: 667 Solved: 350Description
有一个n行m列的整数矩阵,其中1到nm之间的每个整数恰好出现一次。如果一个格子比所有相邻格子(相邻是指有公共边或公共顶点)都小,我们说这个格子是局部极小值。给出所有局部极小值的位置,你的任务是判断有多少个可能的矩阵。Input
输入第一行包含两个整数n和m(1<=n<=4, 1<=m<=7),即行数和列数。以下n行每行m个字符,其中“X”表示局部极小值,“.”表示非局部极小值。Output
输出仅一行,为可能的矩阵总数除以12345678的余数。Sample Input
3 2
X.
..
.XSample Output
60HINT
Source
【分析】
我好蠢啊。。。
保证每个数各不相同,又有大小关系,那么、、数字从小到大填。
其实局部极小值<=8的,这个可以状压,$f[i][j]$表示填了前i个数,局部极小值被填的状态是j的方案数。
有:
$f[i][j]=f[i-1][j]*(p[j]-i+1)+f[i-1][j-(1<<X)]$
但是,还要保证一点是非极小值一定非极小,上面没有保证,
所以枚举哪些非极小弄成了极小,容斥算出正确答案即可。
复杂度?$O(dfs*n*m*8*2^8)$大概是这样吧。。数据很小嘛。。。
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define Mod 12345678
#define LL long long int a[][],num[][],p[];
int n,m;
int bx[]={,,,-,,,-,,-},
by[]={,,,,-,,-,-,};
char s[];
bool vis[][];
LL f[][],ans=; LL get_ans()
{
int cnt=;
for(int i=;i<=n;i++)
for(int j=;j<=m;j++) if(a[i][j]==) num[i][j]=++cnt;
for(int k=;k<=(<<cnt)-;k++)
{
for(int i=;i<=n;i++) for(int j=;j<=m;j++) vis[i][j]=;
for(int i=;i<=n;i++)
for(int j=;j<=m;j++) if(a[i][j]==&&((<<num[i][j]-)&k)==)
{
for(int l=;l<=;l++)
{
int nx=i+bx[l],ny=j+by[l];
vis[nx][ny]=;
}
}
p[k]=;
for(int i=;i<=n;i++)
for(int j=;j<=m;j++) if(vis[i][j]&&a[i][j]==) {p[k]++;vis[i][j]=;}
for(int i=;i<=cnt;i++) if((<<i-)&k) p[k]++;
}
memset(f,,sizeof(f));
f[][]=;
for(int i=;i<=n*m;i++)
for(int j=;j<=(<<cnt)-;j++)
{
f[i][j]=f[i-][j]*(p[j]-i+);f[i][j]%=Mod;
for(int k=;k<=cnt;k++) if((<<k-)&j)
{
f[i][j]+=f[i-][j-(<<k-)];
f[i][j]%=Mod;
}
}
return f[n*m][(<<cnt)-];
} void dfs(int x,int y,int f)
{
if(y==m+) {dfs(x+,,f);return;}
if(x==n+)
{
ans+=f*get_ans();
ans=(ans%Mod+Mod)%Mod;
return;
}
if(a[x][y]==) {dfs(x,y+,f);return;}
bool ok=;
for(int i=;i<=;i++)
{
int nx=x+bx[i],ny=y+by[i];
if(nx<||nx>n||ny<||ny>m) continue;
if(a[nx][ny]==) {ok=;break;}
}
if(ok)
{
a[x][y]=;
dfs(x,y+,-f);
a[x][y]=;
}
dfs(x,y+,f);
} int main()
{
scanf("%d%d",&n,&m);
for(int i=;i<=n;i++)
{
scanf("%s",s+);
for(int j=;j<=m;j++)
{
if(s[j]=='X') a[i][j]=;
else a[i][j]=;
}
}
for(int i=;i<=n;i++)
for(int j=;j<=m;j++) if(a[i][j]==)
{
for(int k=;k<=;k++)
{
int nx=i+bx[i],ny=j+by[i];
if(nx<||nx>n||ny<||ny>m) continue;
if(a[nx][ny]==) {printf("0\n");return ;}
}
}
// memset(vis,1,sizeof(vis));
dfs(,,);
printf("%lld\n",ans);
return ;
}
2017-04-06 10:08:51
【BZOJ 2669】 2669: [cqoi2012]局部极小值 (状压DP+容斥原理)的更多相关文章
- BZOJ2669 [cqoi2012]局部极小值 状压DP 容斥原理
欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - BZOJ2669 题意概括 有一个n行m列的整数矩阵,其中1到nm之间的每个整数恰好出现一次.如果一个格子比所 ...
- BZOJ 2669 CQOI2012 局部极小值 状压dp+容斥原理
题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=2669 题意概述:实际上原题意很简洁了我就不写了吧.... 二话不说先观察一下性质,首先棋盘 ...
- bzoj2669 [cqoi2012]局部极小值 状压DP+容斥
题目传送门 https://lydsy.com/JudgeOnline/problem.php?id=2669 题解 可以发现一个 \(4\times 7\) 的矩阵中,有局部最小值的点最多有 \(2 ...
- 【BZOJ-2669】局部极小值 状压DP + 容斥原理
2669: [cqoi2012]局部极小值 Time Limit: 3 Sec Memory Limit: 128 MBSubmit: 561 Solved: 293[Submit][Status ...
- 【uoj#37/bzoj3812】[清华集训2014]主旋律 状压dp+容斥原理
题目描述 求一张有向图的强连通生成子图的数目对 $10^9+7$ 取模的结果. 题解 状压dp+容斥原理 设 $f[i]$ 表示点集 $i$ 强连通生成子图的数目,容易想到使用总方案数 $2^{sum ...
- 【bzoj2560】串珠子 状压dp+容斥原理
题目描述 有 $n$ 个点,点 $i$ 和点 $j$ 之间可以连 $0\sim c_{i,j}$ 条无向边.求连成一张无向连通图的方案数模 $10^9+7$ .两个方案不同,当且仅当:存在点对 $(i ...
- BZOJ.4145.[AMPPZ2014]The Prices(状压DP)
BZOJ 比较裸的状压DP. 刚开始写麻烦惹... \(f[i][s]\)表示考虑了前\(i\)家商店,所买物品状态为\(s\)的最小花费. 可以写求一遍一定去\(i\)商店的\(f[i]\)(\(f ...
- BZOJ.3058.四叶草魔杖(Kruskal 状压DP)
题目链接 \(2^{16}=65536\),可以想到状压DP.但是又有\(\sum A_i\neq 0\)的问题.. 但是\(2^n\)这么小,完全可以枚举所有子集找到\(\sum A_i=0\)的, ...
- bzoj 5299: [Cqoi2018]解锁屏幕 状压dp+二进制
比较简单的状压 dp,令 $f[S][i]$ 表示已经经过的点集为 $S$,且最后一个访问的位置为 $i$ 的方案数. 然后随便转移一下就可以了,可以用 $lowbit$ 来优化一下枚举. code: ...
- 4455: [Zjoi2016]小星星|状压DP|容斥原理
OrzSDOIR1ak的晨神 能够考虑状压DP枚举子集,求出仅仅保证连通性不保证一一相应的状态下的方案数,然后容斥一下就是终于的答案 #include<algorithm> #includ ...
随机推荐
- 如何发布一个自定义Node.js模块到NPM(详细步骤,附Git使用方法)
咱们闲话不多说,直接开始! 由于我从没有使用过MAC,所以我不保证本文中介绍的操作与MAC一致. 文章开始我先假定各位已经在window全局安装了Node.js,下面开始进行详细步骤介绍: 本文本着, ...
- css_input[checked]复选框去掉默认样式并添加新样式
效果对比: “\2713”实体符号√ :如有兴趣查看详细实体符号请点这里 代码实现: <!DOCTYPE html> <html> <head> <meta ...
- android 自定义View属性
在android开发过程中,用到系统的View时候可以通过XML来定义一些View的属性.比如ImageView: android:src 和android:scaleType为ImageVie ...
- Oracle-AWR报告简介及如何生成【转】
AWR报告 awr报告是oracle 10g及以上版本提供的一种性能收集和分析工具,它能提供一个时间段内整个系统资源使用情况的报告,通过这个报告,我们就可以了解Oracle数据库的整个运行情况,比如硬 ...
- caffe Python API 之可视化
一.显示各层 # params显示:layer名,w,b for layer_name, param in net.params.items(): print layer_name + '\t' + ...
- [转载]FFmpeg完美入门[4] - FFmpeg应用实例
1 用FFserver从文件生成流媒体 一.安装ffmpeg 在ubuntu下,运行sudo apt-get ffmpeg 安装ffmpeg,在其他linux操作系统下,见ffmpeg的编译过程(编译 ...
- ftp,nfs和samba的区别
先从名字上进行理解: 1. FTP(文件传输协议) 2. NFS(网络文件系统) 3. samba 即smb(服务信息块)协议 1 其中FTP 是TCP/IP协议栈所提供的一种子协议,该子协议具体可以 ...
- angular项目中使用jQWidgets
Angular CLI with jQWidgets In this tutorial, we will show you how to use https://cli.angular.io/ alo ...
- python ORM - sqlalchemy 操作使用
python操作数据库 使用 ORM - sqlalchemy,pymsql 安装: pip install pymsq pip install sqlalchemy 一. '''连接数据库''' ...
- linux nginx php-fpm被攻击
1.nginx错误日志:报错 2018/05/30 16:30:55 [error] 8765#0: *1485 connect() to unix:/tmp/php-70-cgi.sock fail ...