P2510 [HAOI2008]下落的圆盘
首先考虑两个圆覆盖的情况,我们可以求出圆心与交点连线 $A$ 的极角
具体就是求出两圆心连线 $B$ 极角加上余弦定理加反余弦求出 $A,B$ 之间夹角 ,然后覆盖了多少就可以得出
但是多个圆覆盖会重复算,所以离线枚举后面的圆,然后把覆盖的区间按极角排序做一遍类似线段覆盖的操作就行了
区间覆盖的时候注意极角可以会算出负数和大于 $2\pi$ 的情况
思路倒挺简单,计算几何实现起来反正就是一堆细节
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
typedef double db;
inline int read()
{
int x=,f=; char ch=getchar();
while(ch<''||ch>'') { if(ch=='-') f=-; ch=getchar(); }
while(ch>=''&&ch<='') { x=(x<<)+(x<<)+(ch^); ch=getchar(); }
return x*f;
}
const db pi=acos(-1.0),pi2=pi*,eps=1e-;
const int N=;
int n;
inline int dcmp(db x) { if(fabs(x)<eps) return ; return x< ? - : ; }
struct Poi {
db x,y;
Poi (db a=,db b=) { x=a,y=b; }
inline Poi operator - (const Poi &tmp) const {
return Poi(x-tmp.x,y-tmp.y);
}
};
inline db Len(Poi A) { return sqrt(A.x*A.x+A.y*A.y); }
inline db angle(Poi A) { return atan2(A.y,A.x); }
struct Circ {
Poi O; db r;
Circ (Poi a=Poi(,),db b=) { O=a,r=b; }
}C[N];
struct dat {
db ang; int type;
dat (db a=,int b=) { ang=a,type=b; }
inline bool operator < (const dat &tmp) const {
return ang<tmp.ang;
}
}D[N];
db work(int p)
{
db res=; int tot=,cnt=;
for(int i=p+;i<=n;i++)
{
db dis=Len(C[i].O-C[p].O);
if( C[p].r+dis<=C[i].r ) return ;//p被完全覆盖
if( dis>=C[p].r+C[i].r || C[i].r+dis<=C[p].r ) continue;//p没被覆盖,记得可能 i 在 p 里面
db alp=acos( (dis*dis+C[p].r*C[p].r-C[i].r*C[i].r)/(*dis*C[p].r) ),k=angle(C[i].O-C[p].O);
db l=k-alp,r=k+alp;//两个交点的极角
if(dcmp(l)<&&dcmp(r)<) { D[++tot]=dat(l+pi2,); D[++tot]=dat(r+pi2,-); continue; }
if(dcmp(l)>=&&r<=pi2) { D[++tot]=dat(l,); D[++tot]=dat(r,-); continue; }
if(dcmp(l)<&&dcmp(r)>=)
{
D[++tot]=dat(l+pi2,); D[++tot]=dat(pi2,-);
D[++tot]=dat(,); D[++tot]=dat(r,-);
}
if(dcmp(l)>=&&r>pi2)
{
D[++tot]=dat(,); D[++tot]=dat(r-pi2,-);
D[++tot]=dat(l,); D[++tot]=dat(pi2,-);
}
}
sort(D+,D+tot+);
for(int i=;i<=tot;i++)
{
if(D[i].type==&&!cnt) res+=D[i].ang-D[i-].ang;//线段覆盖
cnt+=D[i].type;
}
res+=pi2-D[tot].ang;
return C[p].r*res;
}
int main()
{
n=read(); db a,b,c,ans=;
for(int i=;i<=n;i++)
{
scanf("%lf%lf%lf",&a,&b,&c);
C[i]=Circ( Poi(b,c) , a );
}
for(int i=;i<=n;i++) ans+=work(i);
printf("%.3f\n",ans);
return ;
}
P2510 [HAOI2008]下落的圆盘的更多相关文章
- luogu P2510 [HAOI2008]下落的圆盘
LINK:下落的圆盘 计算几何.n个圆在平面上编号大的圆将编号小的圆覆盖求最后所有没有被覆盖的圆的边缘的总长度. 在做这道题之前有几个前置知识. 极坐标系:在平面内 由极点 极轴 和 极径组成的坐标系 ...
- 洛谷P2510 [HAOI2008]下落的圆盘(计算几何)
题面 传送门 题解 对于每个圆,我们单独计算它被覆盖的周长是多少 只有相交的情况需要考虑,我们需要知道相交的那段圆弧的角度,发现其中一个交点和两个圆的圆心可以构成一个三角形且三边都已经知道了,那么我们 ...
- bzoj1043[HAOI2008]下落的圆盘 计算几何
1043: [HAOI2008]下落的圆盘 Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 1598 Solved: 676[Submit][Stat ...
- 【BZOJ1043】[HAOI2008]下落的圆盘 几何
[BZOJ1043][HAOI2008]下落的圆盘 Description 有n个圆盘从天而降,后面落下的可以盖住前面的.求最后形成的封闭区域的周长.看下面这副图, 所有的红色线条的总长度即为所求. ...
- BZOJ 1043 HAOI2008 下落的圆盘 计算几何
题目大意:n个圆盘依次下落.求终于能看到的轮廓线面积 円盘反对! 让我们一起团结起来! 赶走円盘! 咳咳.非常神的一道题 今天去看了题解和白书才搞出来-- 首先我们倒着做 对于每一个圆盘处理出在它之后 ...
- [HAOI2008]下落的圆盘
Description 有n个圆盘从天而降,后面落下的可以盖住前面的.求最后形成的封闭区域的周长.看下面这副图, 所有的红 色线条的总长度即为所求. Input 第一行为1个整数n,N<=100 ...
- bzoj1043 [HAOI2008]下落的圆盘
Description 有n个圆盘从天而降,后面落下的可以盖住前面的.求最后形成的封闭区域的周长.看下面这副图, 所有的红色线条的总长度即为所求. Input 第一行为1个整数n,N<=1000 ...
- BZOJ1043:[HAOI2008]下落的圆盘——题解(配图片)
http://www.lydsy.com/JudgeOnline/problem.php?id=1043 Description 有n个圆盘从天而降,后面落下的可以盖住前面的.求最后形成的封闭区域的周 ...
- Bzoj1313 [HAOI2008]下落的圆盘
有 n 个圆盘从天而降,后面落下的可以盖住前面的.最后按掉下的顺序,在平面上依次测得每个圆盘的圆心和半径,问下落完成后从上往下看,整个图形的周长是多少,即你可以看到的圆盘的轮廓的圆盘的轮廓总长.例如下 ...
随机推荐
- z-tree官方提供的下拉菜单案例
1.z-tree官方提供的下拉菜单案例 <!DOCTYPE html> <HTML> <HEAD> <TITLE> ZTREE DEMO - selec ...
- 牛客网 TaoTao要吃鸡 ( 0/1背包变形 )
题意 : 题目链接 分析 : 如果没有 BUG (即 h == 0 的时候)就是一个普通的 0 / 1 背包 需要讨论一下 h != 0 的情况 此时有就相当于有物品是有特权的 而且背包装有特权的物 ...
- (49)LINUX应用编程和网络编程之四 Linux进程全解
补充: 1. C程序的执行过程: C编译器调用链接器,链接器设置可执行程序文件的启动起始地址(启动例程),启动例程获得内核传递来的 命令行参数和环境变量值,为调用main函数做准备.[实际上该启动例 ...
- (47)LINUX应用编程和网络编程之二Linux文件属性
Linux下的文件系统为树形结构,入口为/ 树形结构下的文件目录: 无论哪个版本的Linux系统,都有这些目录,这些目录应该是标准的.各个Linux发行版本会存在一些小小的差异,但总体来说,还是大体差 ...
- Sql Server2008中自定义函数调用存储过程解决方案
1.开启sql server 2008远程连接 打开sql server配置管理器 配置SSCM,选中左侧的“SQL Server服务”,确保右侧的“SQL Server”以及“SQL Server ...
- 在windows窗口下打开文件夹
System.Diagnostics.Process.Start("Explorer.exe", @"C:\Users\gnt-wangt\Documents\Visua ...
- Oracle数据库表空间创建、添加用户并授权
--创建test表空间CREATE TABLESPACE test_data LOGGING DATAFILE '/u01/app/oracle/oradata/test/test_data.dbf' ...
- Hbase数据备份&&容灾方案
Hbase数据备份&&容灾方案 标签(空格分隔): Hbase 一.Distcp 在使用distcp命令copy hdfs文件的方式实现备份时,需要禁用备份表确保copy时该表没有数据 ...
- JDK中String类的源码分析(一)
1.String类是final的,不允许被继承 /** The value is used for character storage. */ private final char value[]; ...
- Vue左滑组件slider的实现
本文链接:https://blog.csdn.net/latency_cheng/article/details/82983000 slider组件与swiper组件不同,slider滑动时并不翻页, ...