标签:des mode without using i++ too long sele void queue
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5441
#include<iostream> #include<string.h> #include<map> #include<cstdio> #include<cstring> #include<stdio.h> #include<cmath> #include<math.h> #include<algorithm> #include<set> #include<queue> typedef long long ll; using namespace std; const ll mod=1e9+7; const int maxn=1e5+10; const int maxk=5e3+10; const int maxx=1e4+10; const ll maxe=1000+10; #define INF 0x3f3f3f3f3f3f #define Lson l,mid,rt<<1 #define Rson mid+1,r,rt<<1|1 int deep[maxn],node[maxn]; ll ans[maxk]; int n,m,q; struct city { int be,en,va; }c[maxn]; struct Qu { int id,va; }qu[maxk]; void init() { for(int i=1;i<=n;i++) { node[i]=i; deep[i]=1; } } bool cmp(const city a,const city b) { return a.va<b.va; } bool cmp1(const Qu a,const Qu b) { return a.va<b.va; } int Find(int a) { return a==node[a]?a:node[a]=Find(node[a]); } int main() { int t; scanf("%d",&t); while(t--) { memset(ans,0,sizeof(ans)); scanf("%d%d%d",&n,&m,&q); init(); for(int i=0;i<m;i++) { scanf("%d%d%d",&c[i].be,&c[i].en,&c[i].va); } sort(c,c+m,cmp);//按照边的权值进行排序,从小到大 for(int i=0;i<q;i++) { scanf("%d",&qu[i].va); qu[i].id=i; } sort(qu,qu+q,cmp1);//按照询问的大小从小到大排序 int cnt=0; ll tmp=0; for(int i=0;i<m;i++)//因为已经排好序,所以只需遍历一遍就行 { int x=Find(c[i].be); int y=Find(c[i].en); while(c[i].va>qu[cnt].va&&cnt<q)//询问的权值小于当前边的权值 { ans[qu[cnt].id]=tmp; cnt++; } if(x!=y)//代表两个点不在同一个集合中 { ll n1=deep[x],n2=deep[y]; tmp+=(n1+n2)*(n1+n2-1);//合并后的总对数 tmp-=n1*(n1-1)+n2*(n2-1);//减去原来的对数 node[x]=y;//根的变化 deep[y]+=deep[x];//节点数变化 } } while(cnt<q) { ans[qu[cnt++].id]=tmp;//如果已经把所有的边都遍历完了,但是还有询问没有执行完,则所有的边都是该询问的=可以满足的边 } for(int i=0;i<q;i++) printf("%lld\n",ans[i]); } return 0; }
标签:des mode without using i++ too long sele void queue
原文地址:https://www.cnblogs.com/caijiaming/p/9419168.html