$P2212 [USACO14MAR]澆地Watering the Fields$
阿新 • • 發佈:2019-04-20
long long www. gis 根據 cpp tin pac dig turn
\(problem\)
根據 兩點之間距離
\(dis\ = \sqrt{(x1-x2)^2+(y1-y2)^2}\)
然後就是個最短生成樹的模板
帶一點貪心。
\(N<=2000\)
別被這個誤導了。。
邊數最多可能為\((N*(N-1))/2\)
#include <bits/stdc++.h> using namespace std; typedef long long LL; inline LL read() { LL x=0; register char c=getchar(); int f(1); while(!isdigit(c)) { if(c=='-') f=-1; c=getchar();} while(isdigit(c)) x=(x<<1)+(x<<3)+(c&15),c=getchar(); return x*f; } const int N = 2000 + 5 ; int n,c; struct P{ int x; int y; }; P a[N*N]; struct C{ int x; int y; int Cos; }; C f[N*N]; int fa[N]; int cnt(0); int cost(0); inline int Dis(int i,int j) { return pow(a[i].x-a[j].x,2)+pow(a[i].y-a[j].y,2); } inline int find(int x) { return fa[x]==x?fa[x]:fa[x]=find(fa[x]); } inline bool cmp_ (C a,C b) { return a.Cos<b.Cos; } inline void kruskal() { sort(f+1,f+cnt+1,cmp_); int ans(0); int num(0); for(register int i=1;i<=cnt;i++) { int fx=find(f[i].x),fy=find(f[i].y); if(fx==fy) continue ; fa[fx] = fy ; ans += f[i].Cos; if (++ num == n - 1) break ; } if(num == n-1) cout << ans << endl ; else puts("-1") ; } signed main() { n=read(); c=read(); for(register int i=1;i<=n;i++) fa[i]=i; for(register int i=1;i<=n;i++) a[i].x=read(),a[i].y=read(); for(register int i=1;i<=n;i++) for(register int j=i+1;j<=n;j++) { int k=Dis(i,j); if(k >= c) f[++cnt].Cos = k ,f[cnt].x = i , f[cnt].y = j ; } return kruskal() , 0 ; }
$P2212\ [USACO14MAR]澆地Watering\ the\ Fields$