1016: [JSOI2008]最小生成树计数

Time Limit: 1 Sec  Memory Limit: 162 MB
Submit: 6200  Solved: 2518
[Submit][Status][Discuss]

Description

  现在给出了一个简单无向加权图。你不满足于求出这个图的最小生成树,而希望知道这个图中有多少个不同的
最小生成树。(如果两颗最小生成树中至少有一条边不同,则这两个最小生成树就是不同的)。由于不同的最小生
成树可能很多,所以你只需要输出方案数对31011的模就可以了。

Input

  第一行包含两个数,n和m,其中1<=n<=100; 1<=m<=1000; 表示该无向图的节点数和边数。每个节点用1~n的整
数编号。接下来的m行,每行包含两个整数:a, b, c,表示节点a, b之间的边的权值为c,其中1<=c<=1,000,000,0
00。数据保证不会出现自回边和重边。注意:具有相同权值的边不会超过10条。

Output

  输出不同的最小生成树有多少个。你只需要输出数量对31011的模就可以了。

Sample Input

4 6
1 2 1
1 3 1
1 4 1
2 3 2
2 4 1
3 4 1

Sample Output

8
  1. /*
  2. * @Author: LyuC
  3. * @Date: 2017-09-07 21:48:20
  4. * @Last Modified by: LyuC
  5. * @Last Modified time: 2017-09-12 17:52:51
  6. */
  7. /*
  8. 题意:现在给出了一个简单无向加权图。你不满足于求出这个图的最小生成树,而希望知道
  9. 这个图中有多少个不同的最小生成树。(如果两颗最小生成树中至少有一条边不同,则
  10. 这两个最小生成树就是不同的)。由于不同的最小生成树可能很多,所以你只需要输出方
  11. 案数对31011的模就可以了。
  12.  
  13. 思路:每个最小生成树的相同权值的边数是相同的,并且连通性是相同的,只需要枚举每个
  14. 权值的相同连通性,并且是最小生成树中这个权值的个数的方案数,然后组合一下就行了
  15. */
  16. #include <bits/stdc++.h>
  17.  
  18. #define MAXN 105
  19. #define MAXM 1005
  20. #define mod 31011
  21.  
  22. using namespace std;
  23.  
  24. struct Edge{
  25. int u,v,w;
  26. bool operator < (const Edge & other) const{
  27. return w<other.w;
  28. }
  29. }edge[MAXM];
  30. vector<Edge>v[MAXM];
  31. int n,m;
  32. int x,y,z;
  33. int bin[MAXN];
  34. int root[MAXN];
  35. int vis[MAXM];//每种权值用到的数量
  36. int sum;
  37. int la;
  38. int pos;
  39. int res;
  40.  
  41. inline int findx(int x){
  42. int s=x;
  43. while(x!=bin[x])
  44. x=bin[x];
  45. bin[s]=x;
  46. return x;
  47. }
  48.  
  49. inline int Count(int x){
  50. int s=;
  51. while(x){
  52. if(x%)
  53. s++;
  54. x/=;
  55. }
  56. return s;
  57. }
  58.  
  59. inline void init(){
  60. for(int i=;i<=n;i++){
  61. bin[i]=i;
  62. root[i]=i;
  63. }
  64. memset(vis,,sizeof vis);
  65. for(int i=;i<MAXM;i++)
  66. v[i].clear();
  67. res=;
  68. pos=;
  69. sum=;
  70. }
  71.  
  72. int main(){
  73. // freopen("in.txt","r",stdin);
  74. scanf("%d%d",&n,&m);
  75. init();
  76. for(int i=;i<m;i++){
  77. scanf("%d%d%d",&x,&y,&z);
  78. edge[i].u=x;
  79. edge[i].v=y;
  80. edge[i].w=z;
  81. }
  82. sort(edge,edge+m);
  83. //处理每种权值需要的边数
  84. la=-;
  85. for(int i=;i<m;i++){
  86. if(edge[i].w!=la){
  87. la=edge[i].w;
  88. bool flag=false;
  89. for(int j=i;edge[j].w==la;j++){
  90. int fx=findx(edge[j].u);
  91. int fy=findx(edge[j].v);
  92. if(fx!=fy){
  93. flag=true;
  94. bin[fx]=fy;
  95. vis[pos]++;
  96. sum++;
  97. }
  98. v[pos].push_back(edge[j]);
  99. }
  100. pos++;
  101. }
  102. }
  103. if(sum!=n-){
  104. puts("");
  105. return ;
  106. }
  107. for(int i=;i<pos;i++){//枚举每个阶段用到权值的边
  108. if(vis[i]==) continue;
  109. int tol=(<<v[i].size());
  110. int cur=;//可以的方案
  111. for(int j=;j<tol;j++){
  112. if(Count(j)!=vis[i]) continue;
  113. bool flag=true;
  114. memcpy(bin,root,sizeof root);
  115. for(int k=;k<v[i].size();k++){
  116. if((j&(<<k))!=){//如果这条边存在
  117. int fx=findx(v[i][k].u);
  118. int fy=findx(v[i][k].v);
  119. if(fx==fy){
  120. flag=false;
  121. break;
  122. }else{
  123. bin[fx]=fy;
  124. }
  125. }
  126. }
  127. if(flag==true)
  128. cur++;
  129. }
  130. res=res*cur%mod;
  131. memcpy(bin,root,sizeof root);
  132. for(int j=;j<v[i].size();j++){
  133. int fx=findx(v[i][j].u);
  134. int fy=findx(v[i][j].v);
  135. if(fx!=fy){
  136. bin[fx]=fy;
  137. }
  138. }
  139. memcpy(root,bin,sizeof bin);
  140. }
  141. printf("%d\n",res%mod);
  142. return ;
  143. }

1016: [JSOI2008]最小生成树计数的更多相关文章

  1. BZOJ 1016: [JSOI2008]最小生成树计数( kruskal + dfs )

    不同最小生成树中权值相同的边数量是一定的, 而且他们对连通性的贡献是一样的.对权值相同的边放在一起(至多10), 暴搜他们有多少种方案, 然后乘法原理. ----------------------- ...

  2. 【BZOJ 1016】 1016: [JSOI2008]最小生成树计数 (DFS|矩阵树定理)

    1016: [JSOI2008]最小生成树计数 Description 现在给出了一个简单无向加权图.你不满足于求出这个图的最小生成树,而希望知道这个图中有多少个不同的最小生成树.(如果两颗最小生成树 ...

  3. [BZOJ]1016 JSOI2008 最小生成树计数

    最小生成树计数 题目描述 现在给出了一个简单无向加权图.你不满足于求出这个图的最小生成树,而希望知道这个图中有多少个不同的最小生成树.(如果两颗最小生成树中至少有一条边不同,则这两个最小生成树就是不同 ...

  4. 【BZOJ】1016: [JSOI2008]最小生成树计数 深搜+并查集

    最小生成树计数 Description 现在给出了一个简单无向加权图.你不满足于求出这个图的最小生成树,而希望知道这个图中有多少个不同的最小生成树.(如果两颗最小生成树中至少有一条边不同,则这两个最小 ...

  5. 【BZOJ】1016: [JSOI2008]最小生成树计数(kruskal+特殊的技巧)

    http://www.lydsy.com/JudgeOnline/problem.php?id=1016 想也想不到QAQ 首先想不到的是:题目有说,具有相同权值的边不会超过10条. 其次:老是去想组 ...

  6. [BZOJ 1016] [JSOI2008] 最小生成树计数 【DFS】

    题目链接:BZOJ - 1016 题目分析 最小生成树的两个性质: 同一个图的最小生成树,满足: 1)同一种权值的边的个数相等 2)用Kruscal按照从小到大,处理完某一种权值的所有边后,图的连通性 ...

  7. BZOJ.1016.[JSOI2008]最小生成树计数(Matrix Tree定理 Kruskal)

    题目链接 最小生成树有两个性质: 1.在不同的MST中某种权值的边出现的次数是一定的. 2.在不同的MST中,连接完某种权值的边后,形成的连通块的状态是一样的. \(Solution1\) 由这两个性 ...

  8. 大视野 1016: [JSOI2008]最小生成树计数(最小生成树)

    总结:此类题需要耐心观察规律,大胆猜想,然后证明猜想,得到有用的性质,然后解答. 简单的说:找隐含性质. 传送门:http://61.187.179.132/JudgeOnline/problem.p ...

  9. 1016: [JSOI2008]最小生成树计数 - BZOJ

    Description 现在给出了一个简单无向加权图.你不满足于求出这个图的最小生成树,而希望知道这个图中有多少个不同的最小生成树.(如果两颗最小生成树中至少有一条边不同,则这两个最小生成树就是不同的 ...

随机推荐

  1. Java http请求和调用

    关于http get和post请求调用代码以及示例. 参考:http://www.cnblogs.com/zhuawang/archive/2012/12/08/2809380.html http请求 ...

  2. BZOJ1059_矩阵游戏_KEY

    1059: [ZJOI2007]矩阵游戏 Time Limit: 10 Sec Memory Limit: 162 MB Description 小Q是一个非常聪明的孩子,除了国际象棋,他还很喜欢玩一 ...

  3. 18.Llinux-触摸屏驱动(详解)

    本节的触摸屏驱动也是使用之前的输入子系统 1.先来回忆之前第12节分析的输入子系统 其中输入子系统层次如下图所示, 其中事件处理层的函数都是通过input_register_handler()函数注册 ...

  4. Huge Mission

    Huge Mission Problem Description Oaiei is busy working with his graduation design recently. If he ca ...

  5. servlet自动获取前端页面提交数据

    servlet自动获取前端页面jsp提交数据 以下是本人在学习过程中,因前端页面提交参数过多,后台servlet封装实体类过于麻烦而写的一个工具类,应用于jsp/servlet数据提交后,基于MVC+ ...

  6. Java总结篇:Java多线程

    Java总结篇系列:Java多线程 多线程作为Java中很重要的一个知识点,在此还是有必要总结一下的. 一.线程的生命周期及五种基本状态 关于Java中线程的生命周期,首先看一下下面这张较为经典的图: ...

  7. 应试记录2(没有转载标注,NOIP2016复赛过后自动删除)

    #include<stdio.h> #include<string.h> int main() { ]; memset(a, , sizeof(a)); ;i<=;i++ ...

  8. 开源纯C#工控网关+组态软件(三)加入一个新驱动:西门子S7

    一.   引子 首先感谢博客园:第一篇文章.第一个开源项目,算是旗开得胜.可以看到,项目大部分流量来自于博客园,码农乐园,名不虚传^^. 园友给了我很多支持,并提出了很好的改进意见.现加入屏幕分辨率自 ...

  9. 简单Elixir游戏服设计- 创建项目

    反正是写到哪算哪. 创建umbrella项目 mix new simple_game --umbrella 创建model项目 cd simple_game\apps mix new model 创建 ...

  10. Python使用Scrapy爬虫框架全站爬取图片并保存本地(妹子图)

    大家可以在Github上clone全部源码. Github:https://github.com/williamzxl/Scrapy_CrawlMeiziTu Scrapy官方文档:http://sc ...