NOIP2017TG D2T1 奶酪

题目链接

题意:

空间里,分布着一些已知等球,还有$z=0$和$z=h$两个平面。规定相切或相交为“联通”,求两个平面的连通性。

 

程序(100pt):

找出和上、下平面联通的球,转换为求两个集合的连通性,宽搜搞一搞就欧了。

注意一点:判断“联通”的条件用平方后的整式,避开和精度打交道。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#define IL inline
using namespace std;
typedef long long LL;
const LL N=1e3;

    int T,n;
    LL h,r;
    
struct Node{
    LL x,y,z;
    
}a[N+3];

    bool v[N+3];
    int q[N*4+3],hd,tl;

IL LL sq(LL x){
    return x*x;
    
}

IL bool acs(Node a,Node b){
    return sq(r*2)>=sq(a.x-b.x)
                   +sq(a.y-b.y)
                   +sq(a.z-b.z);
    
}

int main(){
    bool flag;
    int u;
    scanf("%d",&T);
    while(T--){
        scanf("%d%lld%lld",&n,&h,&r);
        for(int i=1;i<=n;i++)
            scanf("%lld%lld%lld",&a[i].x,&a[i].y,&a[i].z);
            
        memset(v,0,n+1);
        hd=1;    tl=0;
        for(int i=1;i<=n;i++)
        if(a[i].z<=r){
            q[++tl]=i;
            v[i]=true;
            
        }
        
        flag=false;
        while(hd<=tl){
            u=q[hd++];
            if(a[u].z+r>=h){
                flag=true;
                break;
                
            }
            for(int i=1;i<=n;i++)
            if(i!=u)
            if(acs(a[i],a[u]))
            if(!v[i]){
                q[++tl]=i;
                v[i]=true;
                
            }
                
        }
        
        if(flag)
            printf("Yes
");
        else 
            printf("No
");
        
    }
    
    return 0;
    
}

小结:

5分钟的题目不能耗太多时间。祭奠我当年联赛这道题做的50分……

原文地址:https://www.cnblogs.com/Hansue/p/10990809.html