Description

给定平面上的 N 个点, 其中有一些是红的, 其他是蓝的.现在让你找两条平行的直线, 使得在保证
    不存在一个蓝色的点 被夹在两条平行线之间,不经过任何一个点, 不管是蓝色点还是红色点
的前提下,
被夹在平行线之间的红色点个数最多

Input

第1行: 一个整数 N (1 <= N <= 1000)
   
第2..N+1行: 每行是一个点的坐标以及它的颜色.
                坐标用2个 绝对值<10^9
的整数表示
                颜色用 'R' 或 'B' 表示

Output

第1行: 仅一个整数, 被夹在平行线之间的红色点个数的最大值

Sample Input

4
0 0 R
0 1 B
1 1 R
1 0
B

Sample Output

2
 

先考虑一下如果这两条直线必须与x轴垂直怎么做,我们先可以将所有点按x为第一关键字,y为第二关键字排序,在这个排好序的序列中找到最长的一段红色就是答案了(用线段树维护)

然后我们把坐标系旋转,如果y轴扫过了两点连成的直线,则这两个点的排名就会交换,旋转一周交换的点对为O(N2)个,所以可以用一个线段树来维护区间最长红点数,支持单点修改和查询,复杂度O(N2logN)。

code:

 #include<cstdio>
#include<iostream>
#include<cstring>
#include<algorithm>
#define maxn 1005
using namespace std;
int n,m,a,b,ans,pos[maxn];
char s[];
inline int min(const int &a,const int &b){
int diff=b-a;
return a+(diff&(diff>>));
}
inline int max(const int &a,const int &b){
int diff=b-a;
return b-(diff&(diff>>));
}
struct Point{
int x,y,col;
}point[maxn];
inline bool cmp1(Point a,Point b){
if (a.x!=b.x) return a.x<b.x;
return a.y<b.y;
}
struct Line{
int a,b,x,y;
}line[maxn*maxn];
inline bool cmp2(const Line &a,const Line &b){return 1LL*a.x*b.y<1LL*a.y*b.x;}
inline bool cmp(const Line &a,const Line &b){return 1LL*a.x*b.y==1LL*a.y*b.x;}
struct Seg{
#define ls k<<1
#define rs (k<<1)+1
int val[maxn<<],lmax[maxn<<],rmax[maxn<<],col[maxn<<];
inline void update(int k){
col[k]=col[ls]|col[rs];
lmax[k]=(col[ls])?lmax[ls]:lmax[ls]+lmax[rs];
rmax[k]=(col[rs])?rmax[rs]:rmax[ls]+rmax[rs];
val[k]=max(rmax[ls]+lmax[rs],max(val[ls],val[rs]));
}
inline void modify(int k,int l,int r,int x,int c){
if (l==r){val[k]=lmax[k]=rmax[k]=c^,col[k]=c;return;}
int m=(l+r)>>;
if (x<=m) modify(ls,l,m,x,c); else modify(rs,m+,r,x,c);
update(k);
}
}T;
int main(){
scanf("%d",&n);
for (int i=;i<=n;i++){
scanf("%d%d%s",&point[i].x,&point[i].y,s);
point[i].col=(s[]=='B'),pos[i]=i;
}
sort(point+,point+n+,cmp1);
for (int i=;i<=n;i++) for (int j=i+;j<=n;j++)
line[++m]=(Line){i,j,point[j].x-point[i].x,point[j].y-point[i].y};
sort(line+,line+m+,cmp2);
for (int i=;i<=n;i++) T.modify(,,n,i,point[i].col);
ans=T.val[];
for (int i=,j=;i<=m;i=j){
for (;j<=m&&cmp(line[i],line[j]);j++){
a=line[j].a,b=line[j].b;
T.modify(,,n,pos[b],point[a].col);
T.modify(,,n,pos[a],point[b].col);
swap(pos[a],pos[b]);
ans=max(ans,T.val[]);
}
}
printf("%d\n",ans);
return ;
}

省队集训day6 C的更多相关文章

  1. 省队集训day6 B

    一道AC自动机题···· 一定要把一个节点没有的儿子接到它fai的儿子,否则会卡到n^2的······· #include<cstdio> #include<iostream> ...

  2. 省队集训day6 A

    code: #include<cstdio> #include<iostream> #include<cmath> #include<cstring> ...

  3. 省队集训 Day6 序列

    [题目大意] 给出$n$个数的序列$a_1, a_2, ..., a_n$,有$m$次操作,为下面三种: $A~l~r~d$:区间$[l,r]$,全部加$d$. $M~l~r~d$:区间$[l,r]$ ...

  4. HN2018省队集训

    HN2018省队集训 Day1 今天的题目来自于雅礼的高二学长\(dy0607\). 压缩包下载 密码: 27n7 流水账 震惊!穿着该校校服竟然在四大名校畅通无阻?霸主地位已定? \(7:10\)从 ...

  5. JS省队集训记

    不知不觉省队集训已经结束,离noi也越来越近了呢 论考前实战训练的重要性,让我随便总结一下这几天的考试 Day 1 T1 唉,感觉跟xj测试很像啊?meet in middle,不过这种题不多测是什么 ...

  6. LOJ #6074. 「2017 山东一轮集训 Day6」子序列

    #6074. 「2017 山东一轮集训 Day6」子序列 链接 分析: 首先设f[i][j]为到第i个点,结尾字符是j的方案数,这个j一定是从i往前走,第一个出现的j,因为这个j可以代替掉前面所有j. ...

  7. [2018HN省队集训D9T1] circle

    [2018HN省队集训D9T1] circle 题意 给定一个 \(n\) 个点的竞赛图并在其中钦定了 \(k\) 个点, 数据保证删去钦定的 \(k\) 个点后这个图没有环. 问在不删去钦定的这 \ ...

  8. [2018HN省队集训D8T1] 杀毒软件

    [2018HN省队集训D8T1] 杀毒软件 题意 给定一个 \(m\) 个01串的字典以及一个长度为 \(n\) 的 01? 序列. 对这个序列进行 \(q\) 次操作, 修改某个位置的字符情况以及查 ...

  9. [2018HN省队集训D8T3] 水果拼盘

    [2018HN省队集训D8T3] 水果拼盘 题意 给定 \(n\) 个集合, 每个集合包含 \([1,m]\) 中的一些整数, 在这些集合中随机选取 \(k\) 个集合, 求这 \(k\) 个集合的并 ...

随机推荐

  1. poj 1556 The door

    题目链接:http://poj.org/problem?id=1556 #include<cstdio> #include<cstring> #include<cmath ...

  2. Windows下svn客户端和服务器的安装使用

    svn,全称subversion, 是目前用的较多的开源的版本管理工具.相信有些经历的程序员应该都听说过它. 通常的svn服务器是搭建在Linux中,不过如果作为个人或者单个小组使用的话,就可以把sv ...

  3. openresty nginx 安装过程记录

    转载请注明原始地址 http://www.cnblogs.com/dongxiao-yang/p/4877799.html 一 :系统版本 1 cat /etc/issue: CentOS relea ...

  4. SVM原理(1)

    SVM即支持向量机,是一种机器学习内的二类分类方法,是有监督学习方法. 首先我们需要建立一个分类任务: 首先考虑线性可分的情况:(所谓线性可分就是在N维空间上的两类点,可以用N-1个未知数的函数(超平 ...

  5. 嵌入式Linux的一点学习心得

    Linux本身是一个发展中的操作系统.它有很多前期不完善的机制,被后代用新的机制代替.但是老的机制不可能一下子就消亡,因此由于“历史原因”,会产生很多新旧机制共存的情况.而且Linux的教科书数不胜数 ...

  6. HTTP协议和WEB应用

    一.应用层协议原理 1.套接字(Socket):主机地址+端口地址.(通常为32位IP地址和16位端口号组成,总长度为48位) 2.进程通过套接字来接收和发送报文.因特网运输层将所提供的服务整合成两种 ...

  7. ScheduledExecutorService定时周期运行指定的任务

    一:简单说明 ScheduleExecutorService接口中有四个重要的方法,当中scheduleAtFixedRate和scheduleWithFixedDelay在实现定时程序时比較方便. ...

  8. Android代码混淆

    混淆器(ProGuard) --- 混淆器通过删除从未用过的代码和使用晦涩名字重命名类.字段和方法,对代码进行压缩,优化和混淆.结果是一个比較小的.apk文件,该文件比較难进行逆向project.因此 ...

  9. UILable:显示多种颜色的方法

    借用别人封装好的类库,用来显示同一个UILable上的多种颜色的字. 类库可以直接在次博客中下载,下载后别忘留言哦. 类库使用:主要用了CoreText里面的东西,所以在使用类库之前需要引用CoreT ...

  10. 【AIX】采用vi语法编辑命令行

    AIX中不能像centos那样移动方向键上.下来查询历史键入的命令行记录 可以通过一条命令采用vim的语法编辑命令行,查询历史记录. # set -o vi 在命令行输入上述命令后就可以: ESC+k ...