bzoj4596[Shoi2016]黑暗前的幻想乡 Matrix定理+容斥原理
4596: [Shoi2016]黑暗前的幻想乡
Time Limit: 20 Sec Memory Limit: 256 MB
Submit: 464 Solved: 264
[Submit][Status][Discuss]
Description
四年一度的幻想乡大选开始了,最近幻想乡最大的问题是很多来历不明的妖
怪涌入了幻想乡,扰乱了幻想乡昔日的秩序。但是幻想乡的建制派妖怪(人类)
博丽灵梦和八云紫等人整日高谈所有妖怪平等,幻想乡多元化等等,对于幻想乡
目前面临的种种大问题却给不出合适的解决方案。
风间幽香是幻想乡里少有的意识到了问题的严重性的大妖怪。她这次勇敢的
站了出来参加幻想乡大选。提出包括在幻想乡边境建墙(并让人类出钱),大力
开展基础设施建设挽回失业率等一系列方案,成为了大选年出人意料的黑马并顺
利的当上了幻想乡的大统领。
幽香上台以后,第一项措施就是要修建幻想乡的公路。幻想乡有 N 个城市,
之间原来没有任何路。幽香向选民承诺要减税,所以她打算只修 N- 1 条路将
这些城市连接起来。但是幻想乡有正好 N- 1 个建筑公司,每个建筑公司都想
在修路的过程中获得一些好处。
虽然这些建筑公司在选举前没有给幽香钱,幽香还是打算和他们搞好关系,
因为她还指望他们帮她建墙。所以她打算让每个建筑公司都负责一条路来修。
每个建筑公司都告诉了幽香自己有能力负责修建的路是哪些城市之间的。所
以幽香打算选择 N-1 条能够连接幻想乡所有城市的边,然后每条边都交给一
个能够负责该边的建筑公司修建,并且每个建筑公司都恰好修一条边。
幽香现在想要知道一共有多少种可能的方案呢?两个方案不同当且仅当它
们要么修的边的集合不同,要么边的分配方式不同。
Input
第一行包含一个正整数 N(N<=17), 表示城市个数。
接下来 N-1 行,其中第 i行表示第 i个建筑公司可以修建的路的列表:
以一个非负数mi 开头,表示其可以修建 mi 条路,接下来有mi 对数,
每对数表示一条边的两个端点。其中不会出现重复的边,也不会出现自环。
Output
仅一行一个整数,表示所有可能的方案数对 10^9 + 7 取模的结果。
Sample Input
4
2 3 2 4 2
5 2 1 3 1 3 2 4 1 4 3
4 2 1 3 2 4 1 4 2
Sample Output
17
HINT
Source
这个题有点神
题目规定每个公司都必须修一条,所以我们考虑容斥,和它对着干
强行规定某些公司不修 ans=全都要修-至少一个不修+至少2个不修...
然后考虑排除一些公司不修之后的方案
无向图求生成树个数?被基尔霍夫支配的恐惧逐渐涌上心头。
对啦!基尔霍夫矩阵可以求。具体就是构造基尔霍夫矩阵,
然后去掉任意一行一列(行列标号相同)再对矩阵求行列式值。
从ZJ那里get到一些新东西:
求行列式的值可以把基尔霍夫矩阵高斯消元,保留上三角或者下三角然后对角线求积即可得出答案
然后我就滚去写了,,但是写的时候遇到一些问题:消元时double精度怎么办啊?取模怎么办啊?
从ZJ那里get到一些新东西:
欧几里得求解高斯消元。。O(n^3*log2(n))
具体是:在消元消到第i行时,把i+1~n行的i列位置都消成0
怎么消呢?
先知道行列式性质:
1.任意两行交换位置,行列式值变相反数
2.一行加上其他任意一行的整数倍,行列式值不变
考虑欧几里得把a[j][i]消成0:
把i行和j行辗转相除再相减直到a[j][i]为0啊,,
具体就是参照求gcd的做法啦,
先减,a[j][k]-=(a[i][i]/a[j][i])*a[i][k] (n>=k>=i)
再交换i,j行直到a[j][i]为0
参考一篇论文 https://wenku.baidu.com/view/d5e0e018964bcf84b9d57ba8.html
ZJ的此篇博客 http://www.cnblogs.com/zj75211/p/8035125.html
#include<cstdio>
#include<iostream>
#include<algorithm>
#include<cstring>
#include<vector>
#define ll long long
#define N 25
#define mod 1000000007
using namespace std;
int n,m,cnt[N];ll a[N][N];
struct edge{int u,v;};
vector<edge>g[N]; ll gauss(int x){
int fg=1;
for(int i=1;i<=x;i++)
for(int j=i+1;j<=x;j++)
while(a[j][i]!=0){
ll t=a[i][i]/a[j][i];
for(int k=i;k<=x;k++)
a[i][k]=(a[i][k]-a[j][k]*t)%mod;
for(int k=i;k<=x;k++)
swap(a[i][k],a[j][k]);
fg=-fg;
}
ll res=fg;
for(int i=1;i<=x;i++)res=res*a[i][i]%mod;
if(res<0)res+=mod;
return res;
} void build(int st){
memset(a,0,sizeof(a));
memset(cnt,0,sizeof(cnt));
for(int i=1;i<n;i++){
if(!(st&(1<<(i-1))))continue;
for(int j=0;j<g[i].size();j++){
edge x=g[i][j];
a[x.u][x.v]--;a[x.v][x.u]--;
cnt[x.u]++;cnt[x.v]++;
}
}
for(int i=1;i<=n;i++)a[i][i]=cnt[i];
}
int main(){
scanf("%d",&n);
for(int i=1;i<n;i++){
scanf("%d",&m);
while(m--){
int a,b;
scanf("%d%d",&a,&b);
g[i].push_back((edge){a,b});
}
}
ll ans=0;
for(int st=0;st<(1<<(n-1));st++){
int sum=0;
for(int i=0;i<n-1;i++)if(st&(1<<i))sum++;
build(st);ll x=gauss(n-1);
ans+=((n-1-sum)&1?-1:1)*x;
ans%=mod;
}
ans<0?ans+=mod:1;
cout<<ans;
return 0;
}
bzoj4596[Shoi2016]黑暗前的幻想乡 Matrix定理+容斥原理的更多相关文章
- BZOJ4596: [Shoi2016]黑暗前的幻想乡
Description 四年一度的幻想乡大选开始了,最近幻想乡最大的问题是很多来历不明的妖 怪涌入了幻想乡,扰乱了幻想乡昔日的秩序.但是幻想乡的建制派妖怪(人类) 博丽灵梦和八云紫等人整日高谈所有妖怪 ...
- 洛谷P4336 [SHOI2016]黑暗前的幻想乡 [Matrix-Tree定理,容斥]
传送门 思路 首先看到生成树计数,想到Matrix-Tree定理. 然而,这题显然是不能Matrix-Tree定理硬上的,因为还有每个公司只能建一条路的限制.这个限制比较恶心,尝试去除它. 怎么除掉它 ...
- 【BZOJ4596】[Shoi2016]黑暗前的幻想乡 容斥+矩阵树定理
[BZOJ4596][Shoi2016]黑暗前的幻想乡 Description 幽香上台以后,第一项措施就是要修建幻想乡的公路.幻想乡有 N 个城市,之间原来没有任何路.幽香向选民承诺要减税,所以她打 ...
- bzoj4596/luoguP4336 [SHOI2016]黑暗前的幻想乡(矩阵树定理,容斥)
bzoj4596/luoguP4336 [SHOI2016]黑暗前的幻想乡(矩阵树定理,容斥) bzoj Luogu 题解时间 看一看数据范围,求生成树个数毫无疑问直接上矩阵树定理. 但是要求每条边都 ...
- bzoj 4596 [Shoi2016]黑暗前的幻想乡 矩阵树定理+容斥
4596: [Shoi2016]黑暗前的幻想乡 Time Limit: 20 Sec Memory Limit: 256 MBSubmit: 559 Solved: 325[Submit][Sta ...
- [ZJOI2016]小星星&[SHOI2016]黑暗前的幻想乡(容斥)
这两道题思路比较像,所以把他们放到一块. [ZJOI2016]小星星 题目描述 小Y是一个心灵手巧的女孩子,她喜欢手工制作一些小饰品.她有n颗小星星,用m条彩色的细线串了起来,每条细线连着两颗小星星. ...
- P4336 [SHOI2016]黑暗前的幻想乡
P4336 [SHOI2016]黑暗前的幻想乡 矩阵树定理(高斯消元+乘法逆元)+容斥 ans=总方案数 -(公司1未参加方案数 ∪ 公司2未参加方案数 ∪ 公司3未参加方案数 ∪ ...... ∪ ...
- 【BZOJ4596】黑暗前的幻想乡(矩阵树定理,容斥)
[BZOJ4596]黑暗前的幻想乡(矩阵树定理,容斥) 题面 BZOJ 有\(n\)个点,要求连出一棵生成树, 指定了一些边可以染成某种颜色,一共\(n-1\)种颜色, 求所有颜色都出现过的生成树方案 ...
- 【BZOJ 4596】 4596: [Shoi2016]黑暗前的幻想乡 (容斥原理+矩阵树定理)
4596: [Shoi2016]黑暗前的幻想乡 Time Limit: 20 Sec Memory Limit: 256 MBSubmit: 324 Solved: 187 Description ...
随机推荐
- 使用XIB的UITableViewCell自适应,以及出现的问题进行解决
1.首先需要定义一个属性 @property (nonatomic, strong) UITableViewCell *prototypeCell; 2.在创建完tableView后加上如下代码 se ...
- DOM相关知识
一.查找元素 间接查找 parentNode // 父节点 childNodes // 所有子节点 firstChild // 第一个子节点 lastChild // 最后一个子节点 nextSibl ...
- bzoj千题计划275:bzoj4817: [Sdoi2017]树点涂色
http://www.lydsy.com/JudgeOnline/problem.php?id=4817 lct+线段树+dfs序 操作1:access 操作2:u到根的-v到根的-lca到根的*2+ ...
- bzoj千题计划243:bzoj2325: [ZJOI2011]道馆之战
http://www.lydsy.com/JudgeOnline/problem.php?id=2325 设线段树节点区间为[l,r] 每个节点维护sum[0/1][0/1] 从l的A/B区域到r的 ...
- JAVA_SE基础——52.匿名内部类
电信的电箱烧了,害我断了2天网,真拿命,耽误了 Java匿名内部类的总结: 没有名字的内部类.就是内部类的简化形式.一般只用一次就可以用这种形式.匿名内部类其实就是一个匿名子类对象.想要定义匿名内部类 ...
- github提交代码到服务器的方法
第一种情况,没有冲突:1.git add .//进入到center的项目下将本地文件打包的意思2.git pull origin dev//将服务器的代码下载到本地如果是最新的会提示Already u ...
- cookie中存中文
cookie中存中文 1:想要在cookie中存中文:需要用到URLEncoder(在jdkAPI中有介绍) Cookie cookie = new Cookie("User",U ...
- ICC_lab总结——ICC_lab5:布线&&数字集成电路物理设计学习总结——布线
字丑,禁止转载! 这里将理论总结和实践放在一起了. 布线的理论总结如下所示: 下面是使用ICC进行实践的流程: 本次的布线实验主要达成的目标是: ·对具有时钟树布局后的设计进行可布线性检查 ·完成布线 ...
- lambda匿名函数透析
lambda匿名函数透析 目录 1 匿名函数的作用... 1 2 匿名函数的格式... 1 3 匿名函数实例代码... 3 1 匿名函数的作用 ...
- POJ-1573 Robot Motion模拟
题目链接: https://vjudge.net/problem/POJ-1573 题目大意: 有一个N*M的区域,机器人从第一行的第几列进入,该区域全部由'N' , 'S' , 'W' , 'E' ...