在平面直角坐标系中给定N个圆。已知这些圆两两没有交点,即两圆的关系只存在相离和包含。求这些圆的异或面
积并。异或面积并为:当一片区域在奇数个圆内则计算其面积,当一片区域在偶数个圆内则不考虑。
标签:http ase 交点 一个 存在 output sample it! discuss
地址:http://www.lydsy.com/JudgeOnline/problem.php?id=4561
题目:
在平面直角坐标系中给定N个圆。已知这些圆两两没有交点,即两圆的关系只存在相离和包含。求这些圆的异或面
第一行包含一个正整数N,代表圆的个数。接下来N行,每行3个非负整数x,y,r,表示一个圆心在(x,y),半径为r的
仅一行一个整数,表示所有圆的异或面积并除以圆周率Pi的结果。
思路:
和那个hdu3511一模一样有么有?
直接拿过来改改就ac了
/************************************************************** Problem: 4561 User: weeping Language: C++ Result: Accepted Time:3156 ms Memory:16888 kb ****************************************************************/ #include <bits/stdc++.h> #define MP make_pair using namespace std; const double eps = 1e-8; const int N = 4e5+10; int n,cnt[N]; int cr[N][2],r[N]; pair<int,int>pt[N]; double curx; struct node { int id,f; bool operator < (const node &ta) const { double y1 = cr[id][1] + f * sqrt(1.0 *r[id]*r[id]-1.0*(curx-cr[id][0])*(curx-cr[id][0])); double y2 = cr[ta.id][1] + ta.f * sqrt(1.0 *r[ta.id]*r[ta.id]-1.0*(curx-cr[ta.id][0])*(curx-cr[ta.id][0])); if(fabs(y1-y2)<eps) return f<ta.f; return y1<y2; } }; set<node >st; int main(void) { int n; while(~scanf("%d",&n)) { st.clear(); int tot=0; long long ans=0; for(int i=1;i<=n;i++) { scanf("%d%d%d",&cr[i][0],&cr[i][1],r+i); pt[tot++]=MP(cr[i][0]-r[i],i); pt[tot++]=MP(cr[i][0]+r[i],i-n); cnt[i]=0; } sort(pt,pt+tot); for(int i=0;i<tot;i++) { int k=pt[i].second,up=0,dw=0; curx = pt[i].first; if(k<=0) k+=n,st.erase((node){k,-1}),st.erase((node){k,1}); else { set<node>::iterator it=st.insert((node){k,-1}).first; it++; if(it!=st.end()) up = it->id; it--; if(it!=st.begin()) dw = (--it)->id; if(up==dw&&up) cnt[k]=cnt[up]+1; else if(up&&dw) cnt[k]=max(cnt[up],cnt[dw]); else cnt[k]=1; ans+=(cnt[k]&1?1:-1)*1LL*r[k]*r[k]; st.insert((node){k,1}); } } printf("%lld\n",ans); } return 0; }
bzoj4561: [JLoi2016]圆的异或并 圆的扫描线
标签:http ase 交点 一个 存在 output sample it! discuss
原文地址:http://www.cnblogs.com/weeping/p/7670390.html