bzoj 3262 陌上花开 - CDQ分治 - 树状数组
Description
Input
Output
Sample Input
3 3 3
2 3 3
2 3 1
3 1 1
3 1 2
1 3 1
1 1 2
1 2 2
1 3 2
1 2 1
Sample Output
1
3
0
1
0
1
0
0
1
HINT
1 <= N <= 100,000, 1 <= K <= 200,000
Source
题目大意 三维偏序计数。
首先偏序问题对于5维以下,通常有两种做法
1)k-1层套树(我表示拒绝写这类程序,宁可写O(n2k)大暴力骗分,都不会去写这种"正解")
2)CDQ分治 + (k - 2)层套树(比上面那种方法好多了)
对于3维偏序,显然法2更优秀。可以参考上一道题(bzoj 1176)的做法。
按c维第1关键字,m为第二关键字,s为第三关键字进行排序。
对s进行CDQ分治。统计s在[l, mid]中的元素对[mid + 1, r]中的元素的贡献。用和上一道题同样的做法,将(c, m)看成一个点,左区间中的点看成修改操作,将点(c, m)的权值 + 1,右区间中的点看成查询一个子矩阵的点权和。然后做法一模一样。
当l == r的时候就当成2维偏序问题,用树状数组水过。此时注意对于重复的判断。
Code
/**
* bzoj
* Problem#3262
* Accepted
* Time:1628ms
* Memory:9012k
*/
#include <bits/stdc++.h>
using namespace std;
typedef bool boolean; typedef class Data {
public:
int val[];
int id; Data():val({, , }), id() { } friend boolean operator < (const Data& a, const Data &b) {
for(int i = ; i < ; i++)
if(a.val[i] != b.val[i])
return a.val[i] < b.val[i];
return a.val[] < b.val[];
} boolean operator == (Data b) {
return val[] == b.val[] && val[] == b.val[] && val[] == b.val[];
}
}Data; #define lowbit(x) ((x) & (-x)) typedef class IndexedTree {
public:
int s;
int *lis; IndexedTree():lis(NULL), s() { }
IndexedTree(int s):s(s) {
lis = new int[(s + )];
memset(lis, , sizeof(int) * (s + ));
} inline void add(int idx, int x) {
for(; idx <= s; idx += lowbit(idx))
lis[idx] += x;
} inline int getSum(int idx) {
int rt = ;
for(; idx; idx -= lowbit(idx))
rt += lis[idx];
return rt;
}
}IndexedTree; int n, K;
vector<Data> ds;
IndexedTree it;
int *scores;
int *cnts; inline void init() {
scanf("%d%d", &n, &K);
scores = new int[(n + )];
cnts = new int[(n + )];
memset(scores, , sizeof(int) * (n + ));
memset(cnts, , sizeof(int) * (n + ));
Data d;
for(int i = ; i < n; i++) {
for(int j = ; j < ; j++)
scanf("%d", &d.val[j]);
d.id = i;
ds.push_back(d);
}
} void CDQDividing(int l, int r, vector<Data> &q) {
if(q.empty()) return;
if(l == r) {
for(int i = , j; i < (signed)q.size(); i = j) {
it.add(q[i].val[], );
for(j = i + ; j < (signed)q.size() && q[j] == q[j - ]; j++)
it.add(q[j].val[], );
int c = it.getSum(q[i].val[]);
for(int k = i; k < j; k++)
scores[q[k].id] += c - ;
}
for(int i = ; i < (signed)q.size(); i++)
it.add(q[i].val[], -);
return;
} int mid = (l + r) >> ;
vector<Data> ql, qr;
for(int i = ; i < (signed)q.size(); i++) {
if(q[i].val[] <= mid)
it.add(q[i].val[], ), ql.push_back(q[i]);
else
scores[q[i].id] += it.getSum(q[i].val[]), qr.push_back(q[i]);
} for(int i = ; i < (signed)ql.size(); i++)
it.add(ql[i].val[], -); q.clear();
CDQDividing(l, mid, ql);
CDQDividing(mid + , r, qr);
} inline void solve() {
sort(ds.begin(), ds.end());
it = IndexedTree(K);
// for(int i = 0; i < n; i++)
// printf("%d %d %d\n", ds[i].val[0], ds[i].val[1], ds[i].val[2]);
CDQDividing(, K, ds);
for(int i = ; i < n; i++)
cnts[scores[i]]++;
for(int i = ; i < n; i++)
printf("%d\n", cnts[i]);
} int main() {
init();
solve();
return ;
}
bzoj 3262 陌上花开 - CDQ分治 - 树状数组的更多相关文章
- BZOJ 1176 Mokia CDQ分治+树状数组
1176: [Balkan2007]Mokia Time Limit: 30 Sec Memory Limit: 162 MBSubmit: 1854 Solved: 821[Submit][St ...
- 【bzoj3262】陌上花开 CDQ分治+树状数组
题目描述 有n朵花,每朵花有三个属性:花形(s).颜色(c).气味(m),又三个整数表示.现要对每朵花评级,一朵花的级别是它拥有的美丽能超过的花的数量.定义一朵花A比另一朵花B要美丽,当且仅当Sa&g ...
- bzoj3262: 陌上花开(cdq分治+树状数组)
3262: 陌上花开 题目:传送门 题解: %%%cdq分治 很强大的一个暴力...感觉比分块高级多了 这道题目就是一个十分经典的三维偏序的例题: 一维直接暴力排序x 二维用csq维护y 三维用树状数 ...
- [Bzoj3262]陌上花开(CDQ分治&&树状数组||树套树)
题目链接 题目就是赤裸裸的三维偏序,所以用CDQ+树状数组可以比较轻松的解决,但是还是树套树好想QAQ CDQ+树状数组 #include<bits/stdc++.h> using nam ...
- BZOJ 2683 简单题 cdq分治+树状数组
题意:链接 **方法:**cdq分治+树状数组 解析: 首先对于这道题,看了范围之后.二维的数据结构是显然不能过的.于是我们可能会考虑把一维排序之后还有一位上数据结构什么的,然而cdq分治却可以非常好 ...
- BZOJ_3262_陌上花开_CDQ分治+树状数组
BZOJ_3262_陌上花开_CDQ分治+树状数组 Description 有n朵花,每朵花有三个属性:花形(s).颜色(c).气味(m),用三个整数表示. 现在要对每朵花评级,一朵花的级别是它拥有的 ...
- 【BZOJ4553】[Tjoi2016&Heoi2016]序列 cdq分治+树状数组
[BZOJ4553][Tjoi2016&Heoi2016]序列 Description 佳媛姐姐过生日的时候,她的小伙伴从某宝上买了一个有趣的玩具送给他.玩具上有一个数列,数列中某些项的值可能 ...
- 【bzoj2225】[Spoj 2371]Another Longest Increasing CDQ分治+树状数组
题目描述 给定N个数对(xi, yi),求最长上升子序列的长度.上升序列定义为{(xi, yi)}满足对i<j有xi<xj且yi<yj. 样例输入 8 1 3 3 2 1 1 4 5 ...
- LOJ3146 APIO2019路灯(cdq分治+树状数组)
每个时刻都形成若干段满足段内任意两点可达.将其视为若干正方形.则查询相当于求历史上某点被正方形包含的时刻数量.并且注意到每个时刻只有O(1)个正方形出现或消失,那么求出每个矩形的出现时间和消失时间,就 ...
随机推荐
- VUE中过了一遍还不熟悉的东西
1.computed/watch/和methods computed是依赖于数据来变动的,有缓存,当不需要缓存的时候就用方法,watch不建议乱用,当有异步请求的时候就用watch 写法一样 2.wa ...
- Web API 入门 二 媒体类型
还是拿上面 那篇 Web API 入门 一 的那个来讲 在product类中加一个时间属性
- caffe运行训练脚本时报错:Unknown bottom blob 'data' (layer 'conv1',bottom index 0)
报错的两种报错原因: 1.输入数的路径错误,需要将路径进行修改排查目录是否出错 2.训练原数据格式不对 3.train.prototxt文件中并未设置test层,而在solver层则设置了test的迭 ...
- oauth2.0+app方式 webgis 授权
.认证方式有三种 Oauth2.0, Token-based http/windows 二.用户登录与应用登录区别 两者区别在于:当用户登录时,服务器端平台是否直接识别登录信息和验证登录信息. 应用登 ...
- Unity shader学习之标准的Unity shader
包含光照,可处理多个光源,有光照衰减和阴影的shader,代码如下: 转载请注明出处:http://www.cnblogs.com/jietian331/p/7199311.html Shader & ...
- 交替最小二乘ALS
https://www.cnblogs.com/hxsyl/p/5032691.html http://www.cnblogs.com/skyEva/p/5570098.html 1. 基础回顾 矩阵 ...
- hdu5441 并查集+克鲁斯卡尔算法
这题计算 一张图上 能走的 点对有多少个 对于每个限制边权 , 对每条边排序,对每个查询排序 然后边做克鲁斯卡尔算法 的时候变计算就好了 #include <iostream> #inc ...
- Sitecore CMS中查看标准字段
什么是标准字段? 标准字段是字段及其字段组的集合,用于包含有关Sitecore中项目的可配置元数据.Sitecore中继承自“标准模板”模板的任何项目都将包含这些字段. 可以在“标准模板”模板项找到/ ...
- Python 1.安装
Python是一种开源语言,有很多第三方库. 1. Python3 及相关组件下载及安装 a. Python3下载:https://www.python.org/downloads/->点击以下 ...
- python 读写json数据
json 模块提供了一种很简单的方式来编码和解码JSON 数据. 字符串操作 其中两个主要的函数是json.dumps() 和json.loads() ,要比其他序列化函数库如pickle 的接口少得 ...