• [HAOI2008] 下落的圆盘


    Solution

    我又忘记了 atan2 可以自动处理角度范围555

    #include <bits/stdc++.h>
    using namespace std;
    
    const int N = 10005;
    const double pi = 3.14159265358979;
    const double eps = 1e-6;
    
    namespace solver {
        vector <pair<double,int> > v;
        void clear() {
            v.clear();
        }
        void make(double x,double y) {
            v.push_back({x,1});
            v.push_back({y,0});
        }
        double solve() {
            make(0,0);
            make(2*pi,2*pi);
    
            int cnt=0;
            double ans=0,last=0;
            sort(v.begin(),v.end());
            for(pair<double,int> pr:v) {
                double p=pr.first;
                int w=pr.second;
                if(cnt==0) ans+=p-last;
                last=p;
                if(w==1) cnt++;
                if(w==0) cnt--;
            }
            return ans;
        }
    }
    
    int n;
    double x[N],y[N],r[N];
    
    double calc(double x) {
        while(x<0) x+=pi*2;
        while(x>pi*2) x-=pi*2;
        return x;
    }
    
    signed main() {
        cin>>n;
        for(int i=1;i<=n;i++) cin>>r[i]>>x[i]>>y[i];
        double ans=0;
        for(int i=1;i<=n;i++) {
            double x0=x[i],y0=y[i],r0=r[i];
            solver::clear();
            int flag=0;
            for(int j=i+1;j<=n;j++) {
                double D=sqrt(pow(x[j]-x0,2)+pow(y[j]-y0,2));
                if(D<=r[j]-r0) flag=1;
            }
            if(flag) continue;
            for(int j=i+1;j<=n;j++) {
                double D=sqrt(pow(x[j]-x0,2)+pow(y[j]-y0,2));
                if(D>=r0+r[j]) continue;
                double theta = atan2(y[j]-y0,x[j]-x0);
                theta=calc(theta);
                double phi = acos((D*D+r0*r0-r[j]*r[j])/(2*D*r0));
                double a1 = calc(theta+phi);
                double a2 = calc(theta-phi);
                if(fabs(a2-a1)>eps) {
                    if(a1>a2) {
                        solver::make(a2,a1);
                    }
                    else {
                        solver::make(a2,2*pi);
                        solver::make(0,a1);
                    }
                }
            }
            double tmp=solver::solve();
            ans+=tmp*r0;
        }
        printf("%.3lf
    ",ans);
    }
    
  • 相关阅读:
    CF526D Om Nom and Necklace
    POJ2406 Power Strings
    POJ3461 Oulipo
    luogu P1341 无序字母对
    UOJ 117 欧拉回路
    骑马修栅栏
    vimdiff env.txt export.txt set.txt
    Linux自动执行任务
    消灭 Bug!推荐5款测试员不可不知的bug管理工具!
    Bugzilla使用手册及解决方案
  • 原文地址:https://www.cnblogs.com/mollnn/p/12389328.html
Copyright © 2020-2023  润新知