2016 UESTC Training for Data Structures E - 卿学姐与城堡的墙 CDOJ 1341 树状数组 逆序对 离散化

来源:互联网 发布:银行打击治理电信网络 编辑:程序博客网 时间:2024/04/29 03:32

E题:卿学姐与城堡的墙

N条直线,以y=kx+b的形式给出,问有多少种方式任取两个直线,使这两个直线的交点在x=ux=v之间

对于两个直线ab,怎么判断他们的交点在x=ux=v之间呢

假如直线ax=u时的纵坐标为yau,在x=v时的纵坐标为yav,直线bx=u时的纵坐标为ybu,在x=v时的纵坐标为ybv。假设yauybu的下面,但是yav却在ybv的上面,那中间就是一定有交点的,反之如果yauybu上面,但是yav却在ybv下面,也是一定有交点的,当然还有yau==ybuyav==ybv两种情况。

首先不考虑相等的情况,就是可以把直线按yu升序排序,然后把yv离散化,然后用树状数组维护yv,然后对于每一个yv,大概思路就是查询它的树状数组的前缀和看看前面有多少个比它小的,用总数减一下就可以知道有多少个比它大的,就肯定存在那么多交点(就是相当于逆序对)。

然后我们再继续考虑细节,首先可以按yu升序排序,然后对于每条直线,如果它和上条直线的yu相同,那我们记录这个yu的值的最早出现的位置,假设为last,当前位置为i,则ans +=i-last,因为它可以和前面所有相同的都构成交点,

那么就是考虑右边是否有相同的,右边的话,我们肯定是找大于等于当前yv的数有几个,肯定就是有几个交点,然后加入当前是第i条直线,那么之前有i条直线,然后先树状数组统计小于yv的有几条,假设为x条,那么ans+=i-x,然后树状数组更新当前的yv就行

 

数据水了,貌似没有在有多条直线交在x=u的同一个点和或者交在x=v上的同一个点的情况,各种姿势都能花式水过去


代码:

#include <cstdio>#include <cstdlib>#include <algorithm>using namespace std;#define ll long long#define maxn 200005struct Line{ll y1, y2;bool operator < (Line x)const{return y1 < x.y1;}}line[maxn];int N;ll u, v, data[maxn];ll tree[maxn];void update(int i, ll val){while (i <= N){tree[i] += val;i += i&(-i);}}ll query(int i){ll sum = 0;while (i){sum += tree[i];i -= i&(-i);}return sum;}int main(){//freopen("input.txt", "r", stdin);scanf("%d%lld%lld", &N, &u, &v);ll a, b;for (int i = 0; i < N; ++i){scanf("%lld%lld", &a, &b);line[i].y1 = a*u + b, line[i].y2 = a*v + b;data[i] = line[i].y2;}sort(line, line + N);sort(data, data + N);int num = unique(data, data + N) - data;for (int i = 0; i < N; ++i)line[i].y2 = lower_bound(data, data + num, line[i].y2) - data + 1;ll ans = 0;int last = 0;for (int i = 0; i < N; ++i){if (i > 0 && line[i].y1 == line[i - 1].y1){//++ans;ans += i - last;}else{ans += i - query(line[i].y2 - 1);last = i;}update(line[i].y2, 1);}printf("%lld\n", ans);//system("pause");//while (1);return 0;}

0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 几个月宝宝可以竖着抱 三个月宝宝可以竖着抱吗 三个月宝宝可以竖抱吗 新生儿几个月可以竖着抱 婴儿几个月可以竖着抱 婴儿什么时候可以竖着抱 婴儿什么时候可以竖抱 新生儿几个月可以竖抱 宝宝三个月可以竖着抱吗 小孩几个月可以竖着抱 宝宝什么时候可以竖着抱 宝宝什么时候可以竖抱 孩子几个月可以竖着抱 小孩几个月可以竖抱 孩子几个月可以竖抱 宝宝几个月才能竖着抱 三个月的宝宝可以竖着抱吗 两个多月的宝宝可以竖着抱吗 宝宝什么时候能竖着抱 两个月的宝宝可以竖着抱吗 几个月的宝宝可以竖着抱 几个月婴儿可以竖着抱 婴儿三个月可以竖抱吗 2个月的宝宝可以竖着抱吗 小宝宝几个月可以竖着抱 婴儿两个月可以竖抱吗 婴幼儿几个月可以竖着抱 一个月的宝宝可以竖着抱吗 多大的婴儿可以竖着抱 二个月的宝宝可以竖着抱吗 几个月的宝宝可以竖抱 多大的宝宝可以竖着抱 3个月的宝宝可以竖着抱吗 新生儿多大可以竖着抱 宝宝两个月可以竖着抱吗 两个月宝宝喜欢竖着抱 三个月的婴儿可以竖着抱吗 2个多月的宝宝可以竖着抱吗 新生儿多久可以竖着抱 竖撇的字 一撇一竖是什么字