【题解】A18747.眼红的同学
题目链接:眼红的同学
题干信息很简单,看到数据量之后就不简单了。在数据量小的时候可以使用双层循环暴力的方法来求答案。显然对于这道题而言O(n^2)是完全过不去的。
前置知识:
- 使用树状数组求逆序对
- 会归并排序等分治算法。
如果想要了解跟多信息,可以自行在搜索引擎搜索有关CDQ分治的练习题。
考虑使用分治算法来解决,这是一道经典的三维偏序问题。对于这种坐标相关题目,一个很常见的方法是先对其中一个纬度进行排序。这样子控制一个纬度之后再去查找速度就会快很多。
例如如果控制语文成绩这个维度,按照从大到小的顺序排序后可以得出以下结论:
第i位同学的嫉妒值一定只会被前i-1位同学所影响,排在i后面的所有学生都不会贡献为第i为同学贡献嫉妒值。
接下来的做法跟分治逆序对很像,每次将所有的数字分成两半,以任意一个k为分界线,保证第k个学生的语文成绩低于第k+1个学生的成绩即可。直至区间的长度为1。
由于前半部分的x肯定比后半部分的x要大,可以按照数学成绩再分别被前半部分和后半部分的学生进行排序。这样子依然也不会损失单调性,只要保证前半部分x都比后半部分x大即可。接下来我们就可以遍历 后半部分,在遍历的时候计算单个点所获得的贡献(这些贡献来自于前半部分)。
截至目前已经对两个纬度进行排序了,最后一个纬度可以使用树状数组进行维护。这部分可以借用树状数组求逆序对的思想(请自行查阅)。
时间复杂度也比较好计算,分治的时间复杂度为\(O(log(n) \times n)\)。但是树状数组的单点修改和区间查询也分别是\(O(\log(n))\)级别的。综合下来时间复杂度在\(O(n \times \log(n)^2)\)附近。因为题输入数据比较大,注意常数优化。
参考代码如下:
#include <iostream>
#include <algorithm>
#define int long long
using namespace std;
const int MAXN = 3e5 + 5;
int maximum;
int n, ans[MAXN];
int L[MAXN], R[MAXN];
int bit[MAXN << 1];
struct student{
int x, y, z;
int id, ans, val;
} arr[MAXN];
bool cmp1(student a, student b){
if (a.x != b.x) return a.x > b.x;
if (a.y != b.y) return a.y > b.y;
return a.z > b.z;
}
bool cmp2(student a, student b){
if (a.y != b.y) return a.y > b.y;
if (a.z != b.z) return a.z > b.z;
return a.x > b.x;
}
inline int max(int a, int b, int c){
return max(a, max(b, c));
}
inline int lowbit(int k) {
return k & (-k);
}
void add(int x, int val){
for (int i=x; i<=maximum; i+=lowbit(i))
bit[i] += val;
return ;
}
int query(int x){
int ans = 0;
for (int i=x; i; i-=lowbit(i))
ans += bit[i];
return ans;
}
// 分治闭区间[L,R]
void cdq(int l, int r){
if (l >= r || L[r] == L[l]) return ;
int mid = L[(l + r) >> 1];
if (arr[mid].x == arr[mid+1].x) mid--;
if (mid < l) {
// 往右边寻找中点
mid = R[(l + r) >> 1];
if (mid + 1 > r) return ;
}
cdq(l, mid); cdq(mid+1, r);
sort(arr+l, arr+mid+1, cmp2);
sort(arr+mid+1, arr+r+1, cmp2);
int j = l;
for (int i=mid+1; i<=r; i++){
while (j <= mid && arr[j].y > arr[i].y){
add(arr[j].z, arr[j].val);
j++;
}
arr[i].ans += query(maximum) - query(arr[i].z);
}
// 恢复树状数组
for (int i=l; i<j; i++)
add(arr[i].z, -arr[i].val);
return ;
}
【题解】A18747.眼红的同学的更多相关文章
- 【FCS NOI2018】福建省冬摸鱼笔记 day6【FJOI 2018】福建省选混分滚蛋记 day1
记录一下day6发生的事情吧. 7:30 到达附中求索碑,被人膜,掉RP. 7:50 进考场,6楼的最后一排的最左边的位置,世界上最角落的地方,没有任何想法. 发现电脑时间和别人不一样,赶快调了一下. ...
- USACO 1.4.2 Mother's Mil 母亲的牛奶(DFS)
Description 农民约翰有三个容量分别是A,B,C升的桶,A,B,C分别是三个从1到20的整数,最初,A和B桶都是空的,而C桶是装满牛奶的.有时,约翰把牛奶从一个桶倒到另一个桶中,直到被灌桶装 ...
- codevs——1842 递归第一次
1842 递归第一次 时间限制: 1 s 空间限制: 128000 KB 题目等级 : 白银 Silver 题解 题目描述 Description 同学们在做题时常遇到这种函数 f( ...
- 2016 华南师大ACM校赛 SCNUCPC 非官方题解
我要举报本次校赛出题人的消极出题!!! 官方题解请戳:http://3.scnuacm2015.sinaapp.com/?p=89(其实就是一堆代码没有题解) A. 树链剖分数据结构板题 题目大意:我 ...
- NOIP 2008提高组第三题题解by rLq
啊啊啊啊啊啊今天已经星期三了吗 那么,来一波题解吧 本题地址http://www.luogu.org/problem/show?pid=1006 传纸条 题目描述 小渊和小轩是好朋友也是同班同学,他们 ...
- [题解]扫雷Mine
// 此博文为迁移而来,写于2015年2月6日,不代表本人现在的观点与看法.原始地址:http://blog.sina.com.cn/s/blog_6022c4720102vrft.html 1088 ...
- BZOJ 4247: 挂饰 题解
Description JOI君有N个装在手机上的挂饰,编号为1...N. JOI君可以将其中的一些装在手机上. JOI君的挂饰有一些与众不同--其中的一些挂饰附有可以挂其他挂件的挂钩.每个挂件要么直 ...
- noip2008普及组3题题解-rLq
(第一次写题解,随意喷) (只是前一天的作业哈) (先凑个数) 题目描述 上体育课的时候,小蛮的老师经常带着同学们一起做游戏.这次,老师带着同学们一起做传球游戏.游戏规则是这样的:n个同学站成一个圆圈 ...
- NOIP2008普及组题解
NOIP2008普及组题解 从我在其他站的博客直接搬过来的 posted @ 2016-04-16 01:11 然后我又搬回博客园了233333 posted @ 2016-06-05 19:19 T ...
- HDU 2023题解分析
我想说这道题我还没弄明白我错哪了,交了20多遍一直都是Runtime Error,改了N次还是不对,后来搜了一下,说是数组开小了,又把数组开大,还不对,又改发现一个平均值求错,再改,还不对,洗洗睡吧. ...
随机推荐
- zbar:Qt调用zbar做条码识别
编译: zbar Windows编译:https://gitee.com/vvvj/zbar-windows 下载下来后,直接使用vs来编译就可以了. zbar官网:https://zbar.sour ...
- Django Admin:自动选择当前用户
--转载自:林肯李 该文章写的很好,特转载留待后期备用 背景 在开发 CMS 时,经常需要标记谁创建了记录.Django 为我们提供了一个很好的管理界面.但是当我们只使用默认值时,用户需要自己选择他们 ...
- 在python中通过面向对象方式,实现烤地瓜案例
例子:烤地瓜,不同时间,反馈不同状态,并给不同状态地瓜加入不同味道 烤地瓜时间 0-3分钟,生的 4-7分钟,半生不熟的 8-12分钟,熟了 12分钟以上,已烤熟,糊了 用户可以按自己的意思添加调料 ...
- 鸿蒙HarmonyOS实战-ArkUI组件(页面路由)
一.路由导航 路由导航是指在应用程序中通过路径导航定位到特定页面的过程.路由导航的实现通常采用路由器(router)来进行管理,路由器根据路径的不同值将用户请求导向到不同的页面. 在HarmonyOS ...
- CentOS 6.4(64位)上安装错误libstdc++.so.6(GLIBCXX_3.4.14)解决办法
CentOS 6.4(64位)上安装错误libstdc++.so.6(GLIBCXX_3.4.14)解决办法 (2013-07-29 13:18:01) 转载▼ 分类:linux系统 引用地址: ht ...
- redis 简单整理——复制的原理[二十三]
前言 简单介绍一下复制的原理. 正文 在从节点执行slaveof命令后,复制过程便开始运作,下面详细介绍建立 复制的完整流程. 1)保存主节点(master)信息. 执行slaveof后从节点只保存主 ...
- 重新点亮linux 命令树————网络故障排除[十一五]
前言 简单整理一下网络故障不可达命令. 正文 ping 是否能ping traceroute 追踪路由跳转 mtr 检查数据包是否丢失 nslookup telnet 端口是否可达 tcpdump 能 ...
- 手机配置IPV6
据可靠消息说今年7月份前大部分系统都得支持ipv6,之前也没当回事,突然说要全切,还得验证ipv6的支持情况. 网上找了一堆,发现都过时了,或者行不通,琢磨了一下把华为android的搞定了(流量模式 ...
- 探索Kimi智能助手:如何用超长文本解锁高效信息处理新境界
目前,Kimi备受瞩目,不仅在社交平台上引起了广泛关注,而且在解决我们的实际问题方面也显示出了巨大潜力.其支持超长文本的特性使得我们能够更加灵活地配置信息,避免了频繁与向量数据库进行交互以及编写提示词 ...
- 一个开发者自述:我是如何设计针对冷热读写场景的 RocketMQ 存储系统
简介: 文章中的很多知识点,都是通过云原生编程挑战赛学到的,在一些问题在表述方式.甚至理解上都可能存在一些问题,甚至会有一些谬论:敢于尝试就会犯错,有犯错才会有成长,欢迎各位大佬不舍赐教,多多指正,让 ...