完美网络
Time Limit: 1000ms Memory limit: 65536K 有疑问?点这里^_^
题目描述
完美网络是连通网络的基础上要求去掉网络上任意一条线路,网络仍然是连通网络。求一个连通网络要至少增加多少条边可以成为完美网络。
输入
第一行输入一个数T代表测试数据个数(T<=20)。每个测试数据第一行2个数n,m 分别代表网络基站数和基站间线路数。基站的序号为从1到n。接下来m行两个数代表x,y 代表基站x,y间有一条线路。
(
0 < n < m < 10000)
输出
对于每个样例输出最少增加多少线路可以成为完美网络。每行输出一个结果。
示例输入
2 3 1 1 2 3 2 1 2 2 3
示例输出
2 1
提示
来源
中国海洋大学第三届“朗讯杯”编程比赛高级组试题
示例程序
- #include<stdio.h>
- #include<string.h>
- #include<algorithm>
- #include<queue>
- using namespace std;
- int st[12000];
- int main()
- {
- int T, m, n, u, v;
- scanf("%d", &T);
- while(T--)
- {
- memset(st,0,sizeof(st));
- priority_queue<int, vector<int>, greater<int> >s; //构造优先队列
- scanf("%d%d", &n, &m);
- while(m--)
- {
- scanf("%d%d", &u, &v);
- st[u]++; //每个节点的入度加一
- st[v]++;
- }
- sort(st+1,st+n+1); //对每个节点的入度排序
- for(int i=1;i<=n;i++)
- {
- if(st[i]<2)
- s.push(st[i]); //只要入度小于二就压进队列中,因为构成完美图,每个节点的度数都应该大于等于二
- else
- break;
- }
- int a, b, sum=0;
- while(s.size()>=2)
- {
- a=s.top(); //从队列中取出两个元素,一条边连接两个顶点
- s.pop();
- b=s.top();
- s.pop();
- a++;
- b++;
- sum++;
- if(a<2) //如果节点的入度还是小于二,继续压进队列
- s.push(a);
- if(b<2)
- s.push(b);
- }
- if(!s.empty()) //如果队列中还剩余一个节点,那么条数也要加一
- sum++;
- printf("%d\n", sum);
- }
- return 0;
- }