题目大意

  给你\(n\)条直线\(y=kx+b\),问你从\(y\)值为正无穷大处往下看能看到那些直线。

  \(1\leq n\leq 500000\)

题解

  如果对于两条直线\(l_i,l_j\),\(k_i=k_j\)且\(b_i>b_j\),那么\(l_j\)不可能被看见。

  把直线按\(k\)从小到大排序。如果发生了下图的情况(即\(l_1\)与\(l_3\)的交点的\(x\)坐标比\(l_2\)与\(l_3\)的交点的\(x\)坐标小),则\(l_2\)就不可能被看见。我们可以用栈来维护当前可以看见的直线,如果栈顶那条直线不满足要求,就pop。

  时间复杂度:每个点只会入栈一次,出栈一次,所以时间复杂度是\(O(n)\)的。

代码

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cstdlib>
#include<ctime>
#include<utility>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
struct line
{
double k,b;
int id;
};
line a[500010];
line b[500010];
int cmp(line a,line b)
{
if(a.k!=b.k)
return a.k<b.k;
return a.b<b.b;
}
int q[500010];
int c[500010];
double cross(line a,line b)
{
return (b.b-a.b)/(a.k-b.k);
}
int main()
{
int n;
scanf("%d",&n);
int i;
for(i=1;i<=n;i++)
{
scanf("%lf%lf",&a[i].k,&a[i].b);
a[i].id=i;
}
sort(a+1,a+n+1,cmp);
int m=0;
for(i=1;i<=n;i++)
if(i==n||a[i].k!=a[i+1].k)
b[++m]=a[i];
int t=0;
for(i=1;i<=m;i++)
{
while(t>=2&&cross(b[i],b[q[t-1]])<=cross(b[q[t]],b[q[t-1]])+1e-9)
t--;
q[++t]=i;
}
for(i=1;i<=t;i++)
c[i]=b[q[i]].id;
sort(c+1,c+t+1);
for(i=1;i<=t;i++)
printf("%d ",c[i]);
return 0;
}

【BZOJ1007】【HNOI2008】水平可见直线 几何 单调栈的更多相关文章

  1. [bzoj1007][HNOI2008]水平可见直线_单调栈

    水平可见直线 bzoj-1007 HNOI-2008 题目大意:给你n条直线,为你从上往下看能看见多少跳直线. 注释:能看见一条直线,当且仅当这条直线上存在一条长度>0的线段使得这条线段上方没有 ...

  2. 【BZOJ1007】水平可见直线(单调栈)

    [BZOJ1007]水平可见直线(单调栈) 题解 Description 在xoy直角坐标平面上有n条直线L1,L2,...Ln,若在y值为正无穷大处往下看,能见到Li的某个子线段,则称Li为 可见的 ...

  3. bzoj 1007 [HNOI2008]水平可见直线(单调栈)

    1007: [HNOI2008]水平可见直线 Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 5120  Solved: 1899[Submit][Sta ...

  4. 【洛谷 P3194】 [HNOI2008]水平可见直线 (单调栈)

    题目链接 把线段以斜率为第一关键字,截距为第二关键字升序排序. 然后维护一个单调栈,保证栈中两两线段的交点的\(x\)坐标单调上升就行了.栈中的线段即为所求. #include <cstdio& ...

  5. _bzoj1007 [HNOI2008]水平可见直线【单调栈】

    传送门:http://www.lydsy.com/JudgeOnline/problem.php?id=1007 按斜率排序,去掉斜率相同时,截距较小的直线(即只保留该斜率下截距最大的直线).若当前直 ...

  6. bzoj1007 [HNOI2008]水平可见直线 - 几何 - hzwer.com

    Description Input 第一行为N(0 < N < 50000),接下来的N行输入Ai,Bi Output 从小到大输出可见直线的编号,两两中间用空格隔开,最后一个数字后面也必 ...

  7. BZOJ_1007_ [HNOI2008]_水平可见直线_(单调栈+凸包)

    描述 http://www.lydsy.com/JudgeOnline/problem.php?id=1007 给出一些直线,沿着y轴从上往下看,能看到多少条直线. 分析 由于直线相交,会遮挡住一些直 ...

  8. BZOJ1007: [HNOI2008]水平可见直线(单调栈)

    Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 8638  Solved: 3327[Submit][Status][Discuss] Descripti ...

  9. bzoj1007: [HNOI2008]水平可见直线 单调栈维护凸壳

    在xoy直角坐标平面上有n条直线L1,L2,...Ln,若在y值为正无穷大处往下看,能见到Li的某个子线段,则称Li为可见的,否则Li为被覆盖的.例如,对于直线:L1:y=x; L2:y=-x; L3 ...

随机推荐

  1. python 获取lazada菲律宾站地址库

    import urllib3 import requests import ast import time # 因为lazada返回的数据是json类型,通过解码成字符串类型,为了方便数据操作,使用字 ...

  2. PM2用法简介

    简介 PM2是node进程管理工具,可以利用它来简化很多node应用管理的繁琐任务,如性能监控.自动重启.负载均衡等,而且使用非常简单.引用 全局安装 sudo npm install pm2@lat ...

  3. Alpha冲刺阶段评分发布

    一班 二班 三班  四班

  4. 广州商学院16级软工一班&二班-第一次作业成绩

    广州商学院16级软工一班&二班-第一次作业成绩 作业地址 16软工一班 16软工二班 总结 本次作业反映了几个比较严重的问题: 不按要求阅读相应的文章,回答问题只是敷衍几句. 部分同学的版式混 ...

  5. 用python实现一个回文数

    判断一个整数是否是回文数.回文数是指正序(从左向右)和倒序(从右向左)读都是一样的整数. 示例 1: 输入: 121 输出: true 示例 2: 输入: -121 输出: false 解释: 从左向 ...

  6. BOM、DOM

    window对象 所有浏览器都支持window对象,他表示浏览器窗口. 全局变量是window对象的属性.全局函数是window对象的方法. window的常用方法: window.innerHeig ...

  7. CodeForces Round #529 Div.3

    http://codeforces.com/contest/1095 A. Repeating Cipher #include <bits/stdc++.h> using namespac ...

  8. centos安装bundle文件

    centos安装VMware-Workstation-Full-*.bundle那点事 | 鳗鱼是条狗https://kinggoo.com/centos-vmware.htm Linux 下 VMW ...

  9. JEECG & JEESite Tomcat集群 Session共享

    多台tomcat服务的session共享 memcached与redis - JEECG开源社区 - CSDN博客https://blog.csdn.net/zhangdaiscott/article ...

  10. IdentityServer4【QuickStart】之利用OpenID Connect添加用户认证

    利用OpenID Connect添加用户认证 利用OpenID Connect添加用户认证 在这个示例中我们想要通过OpenID Connect协议将交互用户添加到我们的IdentityServer上 ...