生成生成树计数 --- Matrix-Tree定理(基尔霍夫矩阵树定理)
2017-06-21 11:50
387 查看
定理证明请点这,多看几遍就懂了
模板题点这
题目大意:
*一个有n座城市的组成国家,城市1至n编号,其中一些城市之间可以修建高速公路;
*需要有选择的修建一些高速公路,从而组成一个交通网络;
*计算有多少种方案,使得任意两座城市之间恰好只有一条路径;
模板 :
综合一下,还可以这样写:
(这个是在定理上面加强版,把一些步骤直接在缩合在了一起)
灵活点就是在目标矩阵中,为:(对于一些变形题就这样处理).
无向图的基尔霍夫矩阵: 对角线上表示每个点的度数,若ij之间有边则矩阵ij处为-1
无向图的生成树的数目为: 任意一个n-1阶主子式的行列式的绝对值.
模板题点这
题目大意:
*一个有n座城市的组成国家,城市1至n编号,其中一些城市之间可以修建高速公路;
*需要有选择的修建一些高速公路,从而组成一个交通网络;
*计算有多少种方案,使得任意两座城市之间恰好只有一条路径;
模板 :
#include<iostream> #include<cstdio> #include<cstring> #include<cmath> #include<algorithm> #define ll long long using namespace std; const int maxn=20; int degree[maxn]; //度数矩阵,记录每一个点的度数. //不懂就看下上面那个定理证明. ll a[maxn][maxn]; //矩阵树, 对角线是度数矩阵的每一个数,其余地方为 a[i][j] = a[i][j] - vis[i][j] ; int vis[maxn][maxn]; //临接矩阵,u与v相连就是等于1,否则就是为0.注意是无向边. ll det(int n) //生成树计数:Matrix-Tree定理 //这个是求行列式的精华啊(实质上这个子函数就是用来 //求行列式的值的!)(所以也适用于求行列式值的题) { ll ret=1; for(int i=2; i<=n; i++) //计算任意一个n-1阶行列式的值就是答案. { for(int j=i+1; j<=n; j++){ while(a[j][i]) { ll t=a[i][i]/a[j][i]; //如果要模,则这里就一下 for(int k=i; k<=n; k++) a[i][k]=(a[i][k]-a[j][k]*t); //加一下 for(int k=i; k<=n; k++) swap(a[i][k],a[j][k]); ret=-ret; } } if(a[i][i]==0) return 0; //图无法联通. ret*=a[i][i]; //加一下 } if(ret<0) // 可以缩合为 ((ret % p ) + p ) % p ; ret=-ret; return ret; } //这个就是程序的主要函数,计算行列式的值. int main() { int tcase; scanf("%d",&tcase); while(tcase--) { memset(degree,0,sizeof(degree)); memset(a,0,sizeof(a)); memset(vis,0,sizeof(vis)); int n,m; scanf("%d%d",&n,&m); int u,v; while(m--) { scanf("%d%d",&u,&v); vis[u][v]=1; //相连就是1,否则就是0. vis[v][u]=1; degree[u]++; degree[v]++; } for(int i=1;i<=n;i++){ for(int j=1;j<=n;j++){ if(i==j) a[i][j] = degree[i]; else a[i][j] -= vis[i][j]; } } printf("%lld\n",det(n)); } return 0; }
综合一下,还可以这样写:
(这个是在定理上面加强版,把一些步骤直接在缩合在了一起)
灵活点就是在目标矩阵中,为:(对于一些变形题就这样处理).
无向图的基尔霍夫矩阵: 对角线上表示每个点的度数,若ij之间有边则矩阵ij处为-1
无向图的生成树的数目为: 任意一个n-1阶主子式的行列式的绝对值.
while(m--) { scanf("%d%d",&u,&v); a[u][v]=a[v][u]=-1; //u与v相连,所以在目标矩阵中为-1. degree[u]++; degree[v]++; } for(int i=1;i<=n;i++) a[i][i]=degree[i];
相关文章推荐
- 生成树计数--矩阵树定理(Matrix-Tree定理)
- 生成树的计数 Matrix-Tree(矩阵树)定理
- SPOJ HIGH Highways(生成树计数,Matrix-Tree定理)
- 生成树的计数Matrix-Tree定理
- UVA10766(Organising the Organisation)生成树计数-Matrix-Tree定理
- 生成树的计数Matrix-Tree定理 http://blog.csdn.net/longshuai0821/article/details/7764267
- 【BZOJ1016】【JSOI2008】最小生成树计数 & 【BZOJ1543】生成树计数 (kruskal+matrix_tree定理)
- [矩阵树定理 模板题] BZOJ 1016 [JSOI2008]最小生成树计数 & HDU 4408 Minimum Spanning Tree
- HDU 4408 Minimum Spanning Tree (图的最小生成树计数 Kruskal + Matrix_Tree定理)
- 生成树的计数Matrix-Tree定理
- 生成树计数(Matrix-Tree定理)
- 最小生成树计数 基尔霍夫矩阵树定理
- 最小生成树计数(Kruskal+Matrix-Tree定理)
- 康复计划#5 Matrix-Tree定理(生成树计数)的另类证明和简单拓展
- [bzoj1016][JSOI2008]最小生成树计数 (Kruskal + Matrix Tree 定理)
- 【BZOJ 1016】 [JSOI2008]最小生成树计数(matrix-tree定理做法)
- 基尔霍夫矩阵树定理-Matrix_tree
- 康复计划#5 Matrix-Tree定理(生成树计数)的另类证明和简单拓展
- 康复计划#5 Matrix-Tree定理(生成树计数)的另类证明和简单拓展
- 【生成树计数】Matrix-tree定理学习笔记