标签:
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 19462 Accepted Submission(s): 6095
这道题挺不错的,没有直接给你要结合的点,你要自己去寻找!
我们发现,只有当这个岛屿和其他的距离在10到1000这个范围内才能结合,我们就可以让这一个岛屿和其他的全部尝试一下,符合的就先放在结构体中!
然后就可以用最小生成树来解决了!
1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 #include<cmath> 5 using namespace std; 6 int per[110],cot; 7 struct node 8 { 9 int b,e; 10 double w; 11 }s[10000];//注意结构体要开大点,不然会re 12 bool cmp(node x,node y) 13 { 14 return x.w<y.w; 15 } 16 void init() 17 { 18 int i; 19 for(i=0;i<110;i++) 20 per[i]=i; 21 } 22 int find(int x) 23 { 24 while(x!=per[x]) 25 x=per[x]; 26 return x; 27 } 28 bool join(int x,int y) 29 { 30 int fx=find(x); 31 int fy=find(y); 32 if(fx!=fy) 33 { 34 per[fx]=fy; 35 cot++;//记录连接的边数 36 return true; 37 } 38 return false; 39 } 40 int main() 41 { 42 int i,j,n,n1; 43 double x[1010],y[1010]; 44 scanf("%d",&n); 45 while(n--) 46 { 47 init(); 48 scanf("%d",&n1); 49 for(i=0;i<n1;i++) 50 { 51 scanf("%lf%lf",&x[i],&y[i]); 52 } 53 int k=0; 54 for(i=0;i<n1;i++) 55 { 56 for(j=i;j<n1;j++) 57 { 58 double q=sqrt((x[i]-x[j])*(x[i]-x[j])+(y[i]-y[j])*(y[i]-y[j]));//q来记录两岛屿的距离 59 if(q>=10&&q<=1000) 60 { 61 s[k].b=i; 62 s[k].e=j; 63 s[k].w=q; 64 k++; 65 }//符合要求的放在结构体中 66 67 } 68 } 69 cot=0; 70 sort(s,s+k,cmp); 71 double sum=0; 72 for(i=0;i<k;i++) 73 { 74 if(join(s[i].b,s[i].e)) 75 sum+=s[i].w; 76 } 77 if(cot!=n1-1)//如果边数不等于点数-1就不能全部连通 78 printf("oh!\n"); 79 else 80 printf("%.1lf\n",sum*100); 81 82 } 83 return 0; 84 }
标签:
原文地址:http://www.cnblogs.com/Eric-keke/p/4721077.html