1. 程式人生 > >BZOJ 2429: [HAOI2006]聰明的猴子

BZOJ 2429: [HAOI2006]聰明的猴子

找到 sqrt == sca scanf 4行 int rim online

Time Limit: 10 Sec Memory Limit: 128 MB
Submit: 1502 Solved: 855
[Submit][Status][Discuss]

Description

在一個熱帶雨林中生存著一群猴子,它們以樹上的果子為生。昨天下了一場大雨,現在雨過天晴,但整個雨林的地 表還是被大水淹沒著,部分植物的樹冠露在水面上。猴子不會遊泳,但跳躍能力比較強,它們仍然可以在露出水面 的不同樹冠上來回穿梭,以找到喜歡吃的果實。現在,在這個地區露出水面的有N棵樹,假設每棵樹本身的直徑都 很小,可以忽略不計。我們在這塊區域上建立直角坐標系,則每一棵樹的位置由其所對應的坐標表示(任意兩棵樹 的坐標都不相同)。在這個地區住著的猴子有M個,下雨時,它們都躲到了茂密高大的樹冠中,沒有被大水沖走。由 於各個猴子的年齡不同、身體素質不同,它們跳躍的能力不同。有的猴子跳躍的距離比較遠(當然也可以跳到較近 的樹上),而有些猴子跳躍的距離就比較近。這些猴子非常聰明,它們通過目測就可以準確地判斷出自己能否跳到 對面的樹上。【問題】 現已知猴子的數量及每一個猴子的最大跳躍距離,還知道露出水面的每一棵樹的坐標,你 的任務是統計有多少個猴子可以在這個地區露出水面的所有樹冠上覓食。

Input

第1行為一個整數,表示猴子的個數M(2<=M<=500); 第2行為M個整數,依次表示猴子的最大跳躍距離(每個整數值在1--1000之間); 第3行為一個整數表示樹的總棵數N(2<=N<=1000); 第4行至第N+3行為N棵樹的坐標(橫縱坐標均為整數,範圍為:-1000--1000)。 (同一行的整數間用空格分開)

Output

包括一個整數,表示可以在這個地區的所有樹冠上覓食的猴子數

Sample Input

4
1 2 3 4
6
0 0
1 0
1 2
-1 -1
-2 0
2 2

Sample Output

3

HINT

2<=N <= 1000,1<=M=500


Source

Day2

kruskal 卡堆優化prim 我屮艸芔茻 屠龍寶刀點擊就送
#include <algorithm>
#include <cstdio>
#include <cmath>
#define N 1005
using namespace std;
int cnt,n,m,dis[N],x[N],y[N],fa[N];
double val[N<<1];
double calc(int
x1,int y1,int x2,int y2) {return sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2));} struct Edge { int x,y;double z; bool operator<(Edge a)const { return z<a.z; } }e[N<<10]; bool vis[N]; int find_(int x){return fa[x]==x?x:fa[x]=find_(fa[x]);} int Main() { scanf("%d",&n); for(int i=1;i<=n;++i) scanf("%d",&dis[i]); scanf("%d",&m); for(int i=1;i<=m;++i) fa[i]=i,scanf("%d%d",&x[i],&y[i]); for(int i=1;i<=m;++i) for(int j=i+1;j<=m;++j) e[++cnt]=(Edge){i,j,calc(x[i],y[i],x[j],y[j])}; sort(e+1,e+1+cnt); double maxn=0.0; int num=0; for(int i=1;i<=cnt;++i) { int fx=find_(e[i].x),fy=find_(e[i].y); if(fx==fy) continue; fa[fy]=fx; num++; if(num==m-1) {maxn=e[i].z;break;} } int sum=0; for(int i=1;i<=n;++i) if(dis[i]*1.0>=maxn) sum++; printf("%d",sum); return 0; } int sb=Main(); int main(int argc,char *argv[]){;}

BZOJ 2429: [HAOI2006]聰明的猴子