[HNOI2008]水平可见直线 半平面交

来源:互联网 发布:乌鲁木齐 中亚 知乎 编辑:程序博客网 时间:2024/05/16 00:47

求向直线们的俯视视角中可见的直线,以为是选最大最小斜率然后往中间放。。其实就是半平面交

//#include<bits/stdc++.h>  //#pragma comment(linker, "/STACK:1024000000,1024000000")   #include<stdio.h>  #include<algorithm>  #include<queue>  #include<string.h>  #include<iostream>  #include<math.h>  #include<set>  #include<map>  #include<vector>  #include<iomanip>  using namespace std;  #define ll long long  #define pb push_back  #define FOR(a) for(int i=1;i<=a;i++)    const int maxn=5e4+7;    const double eps=1e-6;struct Line{double a,b;int id;}l[maxn];bool cmp(Line l1,Line l2){if(fabs(l1.a-l2.a)<eps)return l1.b<l2.b;return l1.a<l2.a;}Line st[maxn];bool ans[maxn];int top,n;double crossx(Line l1,Line l2){//解出l1,l2交点横坐标return (l2.b-l1.b)/(l1.a-l2.a);}void insert(Line a){while(top){if(fabs(st[top].a-a.a)<eps)top--;//保留较高直线else if(top>1 && crossx(a,st[top-1])<=crossx(st[top],st[top-1]))top--;else break;}st[++top]=a;}void work(){for(int i=1;i<=n;i++)insert(l[i]);for(int i=1;i<=top;i++)ans[st[i].id]=1;for(int i=1;i<=n;i++)if(ans[i])printf("%d ",i);}int main(){scanf("%d",&n);for(int i=1;i<=n;i++){scanf("%lf%lf",&l[i].a,&l[i].b);l[i].id=i;}sort(l+1,l+n+1,cmp);work();}


原创粉丝点击