生活随笔
收集整理的這篇文章主要介紹了
HDU2724 Tree【最小生成树】
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
題目大意:
有N個城市,每個城市有一個幸福值,如果兩個城市A、B的幸福值分別為VA、VB,如果VA是
素數,或者VB是素數,又或者VA+VB是素數,則城市A和B就能連接一條路,建路的所用花費
為Min(Min(VA , VB),|VA-VB|)。
問:現在想要建幾條路,使得能夠連接所有的城市,所需要建設的最少路程和是多少?
思路:
就是求最小生成樹,先用素數篩選法將素數打表,然后根據題意建邊。最后就是用Prim模板求
最小生成樹就行了。
AC代碼:
[cpp]?view plaincopy
#include<iostream>?? #include<algorithm>?? #include<cstdio>?? #include<cstring>?? using?namespace?std;?? const?int?MAXN?=?660;?? const?int?INF?=?0xffffff0;?? ?? int?vis[MAXN],low[MAXN],Map[MAXN][MAXN],A[MAXN];?? int?prim(int?n)?? {?? ????int?pos,Min,result?=?0;?? ????memset(vis,0,sizeof(vis));?? ?? ????vis[1]?=?1;?? ????pos?=?1;?? ?? ????for(int?i?=?1;?i?<=?n;?i++)?? ????????if(i?!=?pos)?? ????????????low[i]?=?Map[pos][i];?? ?? ????for(int?i?=?1;?i?<?n;?i++)?? ????{?? ????????Min?=?INF;?? ????????for(int?j?=?1;?j?<=?n;?j++)?? ????????{?? ????????????if(vis[j]==0?&&?Min?>?low[j])?? ????????????{?? ????????????????Min?=?low[j];?? ????????????????pos?=?j;?? ????????????}?? ????????}?? ?? ????????result?+=?Min;?? ????????vis[pos]?=?1;?? ?? ????????for(int?j?=?1;?j?<=?n;?j++)?? ????????{?? ????????????if(vis[j]==0?&&?low[j]?>?Map[pos][j])?? ????????????{?? ????????????????low[j]?=?Map[pos][j];?? ????????????}?? ????????}?? ????}?? ?? ????return?result;?? }?? ?? bool?Prime[1000100];?? ?? void?IsPrime()?? {?? ????for(int?i?=?2;?i?<=?1000000;?++i)?? ????????Prime[i]?=?true;?? ????for(int?i?=?2;?i?<=?1000000;?++i)?? ????{?? ????????if(Prime[i])?? ????????{?? ????????????for(int?j?=?i+i;?j?<=?1000000;?j?+=?i)?? ????????????????Prime[j]?=?false;?? ????????}?? ????}?? }?? ?? int?father[MAXN];?? ?? int?find(int?x)?? {?? ????if(x?==?father[x])?? ????????return?father[x];?? ????else?? ????????return?father[x]?=?find(father[x]);?? }?? ?? int?main()?? {?? ????int?T,N;?? ????scanf("%d",&T);?? ????IsPrime();?? ????while(T--)?? ????{?? ????????scanf("%d",&N);?? ????????for(int?i?=?1;?i?<=?N;?++i)?? ????????????for(int?j?=?1;?j?<=?N;?++j)?? ????????????????Map[i][j]?=?INF;?? ????????for(int?i?=?1;?i?<=?N;?++i)?? ????????????scanf("%d",&A[i]);?? ?? ????????for(int?i?=?1;?i?<=?N;?++i)?? ????????????father[i]?=?i;?? ?? ????????for(int?i?=?1;?i?<=?N;?++i)?? ????????{?? ????????????for(int?j?=?i+1;?j?<=?N;?++j)?? ????????????{?? ????????????????if(Prime[A[i]]?||?Prime[A[j]]?||?Prime[A[i]+A[j]])?? ????????????????{?? ????????????????????int?x?=?find(i);?? ????????????????????int?y?=?find(j);?? ????????????????????if(x?!=?y)?? ????????????????????????father[x]?=?y;?? ????????????????????Map[i][j]?=?Map[j][i]?=?min(min(A[i],A[j]),abs(A[i]-A[j]));?? ????????????????}?? ????????????}?? ????????}?? ????????int?flag?=?1;?? ????????for(int?i?=?1;?i?<=?N;?++i)?? ????????{?? ????????????if(find(i)?!=?find(1))?? ????????????????flag?=?0;?? ????????}?? ????????if(flag)?? ????????????printf("%d\n",prim(N));?? ????????else?? ????????????printf("-1\n");?? ????}?? ?? ????return?0;?? } ?
總結
以上是生活随笔為你收集整理的HDU2724 Tree【最小生成树】的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。