Codeforces 1194E. Count The Rectangles
看到 $n<=5000$,直接暴力枚举左右两条竖线
然后考虑怎么计算高度在某个范围内,左端点小于等于某个值,右端点大于等于某个值的横线数量
直接用权值树状数组维护当前高度在某个区间内的横线数量
考虑先固定左边的竖线,然后枚举从左到右枚举右边的竖线,那么随着右边竖线的右移,合法的横线(右端点大于等于某个值的横线)数量只会越来越少
所以枚举右边竖线的时候同时动态维护一个指向当前最左的右端点合法的横线,然后动态维护树状数组就行了
答案也很容易计算,在固定了左右竖线的情况下,设中间有 $p$ 个最小的不可分割的矩形,那么贡献即为 $p(p+1)/2$
(枚举大矩形包含了 $k$ 小矩形,那么就是 $\sum_{k=1}^{p}(p-k+1)$)
然后因为坐标系有负数所以统一加上 $5001$ 即可
复杂度 $n^2 \log 10000$,很稳
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
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 int N=;
struct Line {//竖线
int x,l,r;
Line (int _x=,int _l=,int _r=) { x=_x,l=_l,r=_r; }
inline bool operator < (const Line &tmp) const {
return x!=tmp.x ? x<tmp.x : l<tmp.l;
}
}D[N];
struct Line2 {//横线
int h,l,r;
Line2 (int _h=,int _l=,int _r=) { h=_h,l=_l,r=_r; }
}H1[N],H2[N];
inline bool cmp1(Line2 &A,Line2 &B) { return A.l!=B.l ? A.l<B.l : A.r<B.r; }//把横线按左端点排序
inline bool cmp2(Line2 &A,Line2 &B) { return A.r!=B.r ? A.r<B.r : A.l<B.l; }//按右端点排序
int n,m,md,mh;
struct BIT {//树状数组
int t[N];
inline void init() { memset(t,,sizeof(t)); }
inline void add(int x,int v) { while(x<=m) t[x]+=v,x+=x&-x; }
inline int ask(int x) { int res=; while(x) res+=t[x],x-=x&-x; return res; }
}T;
ll Ans;
int main()
{
n=read(); int a,b,c,d;
for(int i=;i<=n;i++)
{
a=read()+,b=read()+,c=read()+,d=read()+;
m=max(m,max(b,d));
if(a==c)
{
if(b>d) swap(b,d);
D[++md]=Line(a,b,d);
}
else
{
if(a>c) swap(a,c);
H1[++mh]=Line2(b,a,c); H2[mh]=H1[mh];
}
}
sort(D+,D+md+); sort(H1+,H1+mh+,cmp1); sort(H2+,H2+mh+,cmp2);
for(int i=;i<=md;i++)//枚举左边的竖线
{
int l=,r=;//动态维护指针
while(l<=mh&&H1[l].l<=D[i].x) T.add(H1[l].h,),l++;
while(r<=mh&&H2[r].r<D[i].x) T.add(H2[r].h,-),r++;
for(int j=i+;j<=md;j++)
{
while(r<=mh&&H2[r].r<D[j].x)
{
if(H2[r].l<=D[i].x) T.add(H2[r].h,-);//注意要判断是之前加入过的横线
r++;
}
if(D[i].x==D[j].x) continue;//相等不合法
int L=max(D[i].l,D[j].l),R=min(D[i].r,D[j].r);
if(L>=R) continue;//相等不合法
int p=T.ask(R)-T.ask(L-)-; if(p<=) continue;//构不成矩形
Ans+=1ll*p*(p+)/;//累计贡献
}
while(r<=mh)//记得清空树状数组
{
if(H2[r].l<=D[i].x) T.add(H2[r].h,-);
r++;
}
}
printf("%lld\n",Ans);
return ;
}
Codeforces 1194E. Count The Rectangles的更多相关文章
- Codeforces - 1194E - Count The Rectangles - 扫描线
https://codeforc.es/contest/1194/problem/E 给5000条正常的(同方向不会重叠,也不会退化成点的)线段,他们都是平行坐标轴方向的,求能组成多少个矩形. 先进行 ...
- Codeforces 1197E Count The Rectangles(树状数组+扫描线)
题意: 给你n条平行于坐标轴的线,问你能组成多少个矩形,坐标绝对值均小于5000 保证线之间不会重合或者退化 思路: 从下到上扫描每一条纵坐标为y的水平的线,然后扫描所有竖直的线并标记与它相交的线,保 ...
- Educational Codeforces Round 68 E. Count The Rectangles
Educational Codeforces Round 68 E. Count The Rectangles 传送门 题意: 给出不超过\(n,n\leq 5000\)条直线,问共形成多少个矩形. ...
- Codeforces 372 B. Counting Rectangles is Fun
$ >Codeforces \space 372 B. Counting Rectangles is Fun<$ 题目大意 : 给出一个 \(n \times m\) 的 \(01\) ...
- codeforces 713B B. Searching Rectangles(二分)
题目链接: B. Searching Rectangles time limit per test 1 second memory limit per test 256 megabytes input ...
- codeforces D. Count Good Substrings
http://codeforces.com/contest/451/problem/D 题意:给你一个字符串,然后找出奇数和偶数长度的子串的个数,这些字串符合,通过一些连续相同的字符合并后是回文串. ...
- CodeForces - 1189E Count Pairs(平方差)
Count Pairs You are given a prime number pp, nn integers a1,a2,…,ana1,a2,…,an, and an integer kk. Fi ...
- Codeforces 1188B - Count Pairs(思维题)
Codeforces 题面传送门 & 洛谷题面传送门 虽说是一个 D1B,但还是想了我足足 20min,所以还是写篇题解罢( 首先注意到这个式子里涉及两个参数,如果我们选择固定一个并动态维护另 ...
- codeforces 451D Count Good Substrings
题意:给定一个字符串,求有多少个奇数子串和多少偶数子串为 “回文串” 这边回文串很特殊之含有 ab 两种字母 而且 相邻的字母相同则消去一个 一直到不存在相邻的相同. 思路: 在这种串 ...
随机推荐
- C++入门经典-例8.6-多重继承的构造顺序
1:单一继承是先调用基类的构造函数,然后调用派生类的构造函数,但多重继承将如何调用构造函数呢?多重继承中的基类构造函数被调用的顺序以派生表中声明的顺序为准.派生表就是多重继承定义中继承方式后面的内容, ...
- IDEA找回Run Dashboard
特别提示:本人博客部分有参考网络其他博客,但均是本人亲手编写过并验证通过.如发现博客有错误,请及时提出以免误导其他人,谢谢!欢迎转载,但记得标明文章出处:http://www.cnblogs.com/ ...
- 石川es6课程---5、函数-参数
石川es6课程---5.函数-参数 一.总结 一句话总结: ` 收集参数:收集剩余的参数,必须当到最后一个参数位置:function show(a, b, ...args) { ` 展开参数:展开数组 ...
- better-scroll 的介绍
配置项中的 probeType 属性,是number,当值为 0 ,不会实时监听 scroll 事件,设置为 2 - 3 ,可以实时监听 scroll 事件 pullUpload 选项,设置为 fal ...
- PHP中try catch的用法
异常(Exception)用于在指定的错误发生时改变脚本的正常流程. 什么是异常? PHP 5 提供了一种新的面向对象的错误处理方法. 异常处理用于在指定的错误(异常)情况发生时改变脚本的正常流程.这 ...
- js携带参数跳转controller返回页面
upauth:function(){ var record = myForm.getRecord(); var companywyId = record.get("companyId&quo ...
- Mac下WebStorm直接运行ReactNative项目
1.首先点击WebStorm右上方的下拉箭头弹出的Edit Configurations…. 2.然后会进入一个配置页面.点击左上方的+.在弹出的列表中选中npm. 3.在右边的配置框中,先选择Com ...
- Jsp中的四个域对象
四个域对象: pageContext page域 request request域 session session域 application ...
- Python学习笔记:读取Excel的xlrd模块
一.安装xlrd 可以使用命令行安装也可使用pycharm进行安装 表示xlrd库已经安装成功,安装成功后,我们就可以导入使用了. 二.xlrd说明 (1.单元格常用的数据类型包括 0:empty(空 ...
- 用泛型方法Java从实体中提取属性值,以及在泛型方法中的使用
public <T> T getFieldValue(Object target, String fieldName, Class<T> typeName) { try { O ...