| 记录编号 |
147307 |
评测结果 |
AAAAAAAAAA |
| 题目名称 |
1313.[HAOI 2008]下落的圆盘 |
最终得分 |
100 |
| 用户昵称 |
天一阁 |
是否通过 |
通过 |
| 代码语言 |
C++ |
运行时间 |
0.121 s |
| 提交时间 |
2015-01-29 07:08:00 |
内存使用 |
0.34 MiB |
显示代码纯文本
#include<iostream>
#include<cstdio>
#include<cstring>
#include<vector>
#include<cmath>
#include<algorithm>
#define Maxn 1010
#define LD double
#define pi 3.14159265358
using namespace std;
struct node{
LD x,y,r;
void scan(){
scanf("%lf%lf%lf",&r,&x,&y);
}
}C[Maxn];
struct sege{LD l,r;};
int n;
LD ans=0;
vector<sege> V;
bool operator<(sege a,sege b){
return a.l<b.l;
}
LD dist(node a,node b){
return (LD)sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));
}
bool cover(node a,node b){
if(a.r>=b.r+dist(a,b)) return true;
return false;
}
void insert(node a,node b){
LD d=dist(a,b);
LD tmp=(a.r*a.r-b.r*b.r+d*d)/(2*d);
LD l=atan2(a.x-b.x,a.y-b.y),len=acos(tmp/a.r);
V.push_back((sege){l-len,l+len});
}
LD solve(int x){
for(int i=x+1;i<=n;i++) if(cover(C[i],C[x])) return 0;
V.clear();
for(int i=x+1;i<=n;i++){
if(!cover(C[x],C[i])&&C[x].r+C[i].r>=dist(C[x],C[i])){
insert(C[x],C[i]);
}
}
for(int i=0;i<V.size();i++){
if(V[i].l<0) V[i].l+=2*pi;
if(V[i].r<0) V[i].r+=2*pi;
if(V[i].l>V[i].r) V.push_back((sege){0,V[i].r}),V[i].r=2*pi;
}
LD res=0,now=0;
sort(V.begin(),V.end());
for(int i=0;i<V.size();i++){
if(V[i].l<=now) now=max(now,V[i].r);
else res+=V[i].l-now,now=V[i].r;
}
res+=2*pi-now;
return C[x].r*res;
}
int main(){
freopen("disc.in","r",stdin);
freopen("disc.out","w",stdout);
scanf("%d",&n);
for(int i=1;i<=n;i++) C[i].scan();
for(int i=1;i<=n;i++) ans+=solve(i);
printf("%.3lf\n",ans);
return 0;
}