【uoj#37/bzoj3812】[清华集训2014]主旋律 状压dp+容斥原理
求一张有向图的强连通生成子图的数目对 $10^9+7$ 取模的结果。
题解
状压dp+容斥原理
设 $f[i]$ 表示点集 $i$ 强连通生成子图的数目,容易想到使用总方案数 $2^{sum[i]}$ 减去不为强连通图的方案数得到强连通图的方案数,其中 $sum[i]$ 表示点集 $i$ 中边的数目。
考虑什么样的图不是强连通图:缩点后入度为0的强连通分量对应的点集不是全集。
枚举这些入度为0的强连通分量对应的点集,由于无法保证只有这些点构成的入度为0的强连通分量,因此需要进一步容斥。推之可以发现容斥系数与这些点形成的强连通分量数目的奇偶性有关。
更具体来讲,形成奇数个强连通分量时容斥系数为正(即减去),形成偶数个强连通分量为负(即加上)。
设 $g[i]=i个点形成奇数个强连通分量的方案数-i个点形成偶数个强连通分量的方案数$ ,那么枚举 $i$ 中编号最小的点所在连通块 $i-j$ (即枚举剩下部分 $x$ 不与编号最小的点相连的强连通分量 $j$ ),则有 $g[i]=-\sum\limits_{j\subset x}f[i-j]·g[j]$ 。注意此时的 $g$ 不包含 $i$ 只形成一个强连通分量的情况,以便下面 $f$ 的容斥。
那么枚举钦定的入度为0的强连通分量 $j$ ,就有 $f$ 的转移:$f[i]=2^{sum[i]}-\sum\limits_{j\subset i}2^{sum[i]-w[j]}·g[j]$ ,其中 $w[j]$ 表示 $i$ 向 $j$ 连边的数目,表示钦定的点不能被连边,其它的随意连。
最后将只有一个强连通分量的方案 $f[i]$ 算进 $g[i]$ 。
答案就是 $f[2^n-1]$ 。
时间复杂度 $O(3^n)$
#include <cstdio>
#define N 32775
#define mod 1000000007
typedef long long ll;
int in[N] , out[N] , cnt[N] , sum[N] , w[N];
ll b[215] , f[N] , g[N];
void dfs(int i , int j)
{
if(i & (j - 1)) dfs(i , i & (j - 1));
w[j] = w[j - (j & -j)] + cnt[in[j & -j] & i];
}
int main()
{
int n , m , i , j , x , y;
scanf("%d%d" , &n , &m);
b[0] = 1;
for(i = 1 ; i <= m ; i ++ )
{
scanf("%d%d" , &x , &y) , x -- , y -- ;
in[1 << y] |= 1 << x , out[1 << x] |= 1 << y;
b[i] = b[i - 1] * 2 % mod;
}
for(i = 1 ; i < (1 << n) ; i ++ )
{
x = i - (i & -i) , cnt[i] = cnt[x] + 1 , sum[i] = sum[x] + cnt[in[i & -i] & i] + cnt[out[i & -i] & i] , f[i] = b[sum[i]];
dfs(i , i);
for(j = x ; j ; j = x & (j - 1)) g[i] = (g[i] - f[i ^ j] * g[j] % mod + mod) % mod;
for(j = i ; j ; j = i & (j - 1)) f[i] = (f[i] - b[sum[i] - w[j]] * g[j] % mod + mod) % mod;
g[i] = (g[i] + f[i]) % mod;
}
printf("%lld\n" , f[(1 << n) - 1]);
return 0;
}
【uoj#37/bzoj3812】[清华集训2014]主旋律 状压dp+容斥原理的更多相关文章
- 【UOJ#37】 [清华集训2014] 主旋律
题目链接 题目描述 给定一张强联通图,求有多少种边的存在情况满足图依然强联通. \(n\leq15\) Sol 首先正难则反,考虑用总数减去不强联通的. 考虑一张不强联通的图,缩点后一定是一个 DAG ...
- uoj#37. 【清华集训2014】主旋律(状压dp+容斥)
传送门 第一眼容斥,然后我就死活容不出来了-- 记\(f_i\)为点集\(i\)中的点强联通的方案数,那么就是总的方案数减去使\(i\)不连通的方案数 如果\(i\)不连通的话,我们可以枚举缩点之后拓 ...
- UOJ#37. 【清华集训2014】主旋律
题目大意: 传送门 题解: 神题……Orz. 首先正难则反. 设$f_S$表示选取点集状态为s时,这部分图可以构成非强联通图的方案数. 设$p_{S,i}$表示点集s缩点后有i个入度为0点的方案数,保 ...
- BZOJ3812 清华集训2014 主旋律
直接求出强联通生成子图的数量较难,不妨用所有生成子图的数量减去非强联通的. 非强联通生成子图在所点后满足编号最小的点所在的强联通分量不是全集. 由于$n$很小,我们可以考虑状态压缩. 对于点集$S$, ...
- 【bzoj2560】串珠子 状压dp+容斥原理
题目描述 有 $n$ 个点,点 $i$ 和点 $j$ 之间可以连 $0\sim c_{i,j}$ 条无向边.求连成一张无向连通图的方案数模 $10^9+7$ .两个方案不同,当且仅当:存在点对 $(i ...
- uoj 41 【清华集训2014】矩阵变换 婚姻稳定问题
[清华集训2014]矩阵变换 Time Limit: 20 Sec Memory Limit: 256 MB 题目连接 http://uoj.ac/problem/41 Description 给出 ...
- BZOJ2669 [cqoi2012]局部极小值 状压DP 容斥原理
欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - BZOJ2669 题意概括 有一个n行m列的整数矩阵,其中1到nm之间的每个整数恰好出现一次.如果一个格子比所 ...
- 4455: [Zjoi2016]小星星|状压DP|容斥原理
OrzSDOIR1ak的晨神 能够考虑状压DP枚举子集,求出仅仅保证连通性不保证一一相应的状态下的方案数,然后容斥一下就是终于的答案 #include<algorithm> #includ ...
- UOJ#46. 【清华集训2014】玄学
传送门 分析 清华集训真的不是人做的啊嘤嘤嘤 我们可以考虑按操作时间把每个操作存进线段树里 如果现在点x正好使一个整块区间的右端点则更新代表这个区间的点 我们不难发现一个区间会因为不同的操作被分成若干 ...
随机推荐
- 从零开始自学 Java Web
目录: 1.Java JDK下载安装及配置 2.eclipse下载与安装并测试 3.eclipse快捷键 4.Tomcat 下载与安装 5.Tomcat部署Web应用 6.Eclipse中配置Tomc ...
- 为什么 Action/ViewController/ProperttyEditor不可见或不可用?
英文版:https://documentation.devexpress.com/eXpressAppFramework/112818/Concepts/Extend-Functionality/De ...
- 动态加载与插件系统的初步实现(二):AppDomain卸载与代理
前一篇文章简单展示了类型发现和MEF使用,本文初步进入AppDomain相关内容. CLR程序运行时会创建默认程序集容器即AppDomain,默认AppDomain不支持卸载其程序集,但CLR支持创建 ...
- Centos6.8操作防火墙
设置防火墙iptables开放3306接口 在/etc/sysconfig下面有个iptables文件,在控制台输入命令 iptables -I INPUT -p tcp --dport 3306 - ...
- Unity在OpenGL模式下Shader编译报错
报错信息 GLSL compilation failed: 0(21) : error C7528: OpenGL reserves names containing '__' 双击报错VS自动打开V ...
- C#如何在各类控件中输入\输出数据
文本框:TextBox Text - 按钮文字 TextBox.text=""; s=TextBox.text; 单选按钮+复选按钮 RadioButton,CheckBox Te ...
- 如何批量删除QQ浏览器指定历史记录和导出指定的历史记录
QQ浏览器的历史记录只有清空历史记录和删除选中项两个功能.有时我不想删除所有的历史记录,只是想删除指定的历史记录保留对自己有用的历史记录,方便自己以后查找.但是删除选中项功能只能一项一项的选择,才能批 ...
- sqli-labs学习笔记 DAY6
DAY 6 sqli-labs lesson 30 与上一题一样,需要用到HPP 查看源代码,参数两边加上了双引号,直接使用lesson 26a与lesson 27a的脚本即可 sqli-labs l ...
- date命令详解
基础命令学习目录首页 原文链接:https://www.cnblogs.com/qmfsun/p/4598650.html date "+今天是%Y-%d-%m,现在是%H:%M:%S&qu ...
- ipcs命令详解
基础命令学习目录首页 多进程间通信常用的技术手段包括共享内存.消息队列.信号量等等,Linux系统下自带的ipcs命令是一个极好的工具,可以帮助我们查看当前系统下以上三项的使用情况,从而利于定位多进程 ...