线段树+离线 hdu5654 xiaoxin and his watermelon candy
传送门:点击打开链接
题意:一个三元组假设满足j=i+1,k=j+1,ai<=aj<=ak,那么就好的。如今告诉你序列。然后Q次询问。每次询问一个区间[l,r],问区间里有多少个三元组满足要求
思路:刚開始看错题目了,原来三元组是连续3个,这作为bc最后一题也太水了把。
。
。
先一遍预处理。把连续3个满足条件的找出来,放到还有一个数组里排序去重,用这个数组来给三元组哈希。再扫一遍给三元组在之前那个排序好的数组里二分一下得到下标,大概就是哈希一下,用一个数字来表示。
之后的查询。事实上就是。在区间内。不同的数字有多少个。
这是一个很经典的线段树+离线的题目,仅仅要按右区间排序,然后xjb搞即可了,就不多说了。
。
#include <map>
#include <set>
#include <cmath>
#include <ctime>
#include <stack>
#include <queue>
#include <cstdio>
#include <cctype>
#include <string>
#include <vector>
#include <cstring>
#include <iomanip>
#include <iostream>
#include <algorithm>
#include <functional>
#define fuck(x) cout<<"["<<x<<"]"
#define FIN freopen("input.txt","r",stdin)
#define FOUT freopen("output.txt","w+",stdout)
using namespace std;
typedef long long LL;
typedef pair<int, int> PII; const int MX = 2e5 + 5; struct Data {
int a, b, c;
bool operator<(const Data &P) const {
if(a == P.a) {
if(b == P.b) return c < P.c;
return b < P.b;
}
return a < P.a;
}
bool operator==(Data &P) const {
return a == P.a && b == P.b && c == P.c;
}
} D[MX], dt;
struct Seg {
int l, r, id;
bool operator<(const Seg &P) const {
return r < P.r;
}
} S[MX];
int n, Q, ans[MX];
int sum[MX << 2], col[MX << 2];
int A[MX], pre[MX], pos[MX], sz; #define lson l, m, rt << 1
#define rson m + 1, r, rt << 1 | 1
void push_up(int rt) {
sum[rt] = sum[rt << 1] + sum[rt << 1 | 1];
}
void push_down(int rt, int len) {
if(col[rt]) {
int sr = len >> 1, sl = len - sr;
col[rt << 1] += col[rt]; col[rt << 1 | 1] += col[rt];
sum[rt << 1] += col[rt] * sl; sum[rt << 1 | 1] += col[rt] * sr;
col[rt] = 0;
}
}
void build(int l, int r, int rt) {
sum[rt] = col[rt] = 0;
if(l == r) return;
int m = (l + r) >> 1;
build(lson); build(rson);
}
int query(int p, int l, int r, int rt) {
if(l == r) return sum[rt];
int m = (l + r) >> 1;
push_down(rt, r - l + 1);
if(p <= m) return query(p, lson);
else return query(p, rson);
}
void update(int L, int R, int l, int r, int rt) {
if(L <= l && r <= R) {
sum[rt] += r - l + 1;
col[rt] += 1;
return;
}
int m = (l + r) >> 1;
push_down(rt, r - l + 1);
if(L <= m) update(L, R, lson);
if(R > m) update(L, R, rson);
push_up(rt);
} int main() {
int T; //FIN;
scanf("%d", &T);
while(T--) {
sz = 0;
scanf("%d", &n);
build(1, n, 1); for(int i = 1; i <= n; i++) scanf("%d", &A[i]);
for(int i = 3; i <= n; i++) {
if(A[i - 2] <= A[i - 1] && A[i - 1] <= A[i]) {
sz++;
D[sz].a = A[i - 2]; D[sz].b = A[i - 1]; D[sz].c = A[i];
}
}
sort(D + 1, D + 1 + sz);
sz = unique(D + 1, D + 1 + sz) - D - 1;
for(int i = 1; i <= sz; i++) pos[i] = 0;
for(int i = 1; i <= n; i++) {
if(i >= 3 && A[i - 2] <= A[i - 1] && A[i - 1] <= A[i]) {
dt.a = A[i - 2]; dt.b = A[i - 1]; dt.c = A[i];
int id = lower_bound(D + 1, D + 1 + sz, dt) - D;
pre[i] = pos[id];
pos[id] = i;
} else pre[i] = -1;
} scanf("%d", &Q);
for(int i = 1; i <= Q; i++) {
S[i].id = i;
scanf("%d%d", &S[i].l, &S[i].r);
}
sort(S + 1, S + 1 + Q); int cur = 1;
for(int r = 1; r <= n; r++) {
if(pre[r] != -1) update(pre[r] + 1, r, 1, n, 1);
while(cur <= Q && S[cur].r == r) {
if(S[cur].l + 2 <= S[cur].r) ans[S[cur].id] = query(S[cur].l + 2, 1, n, 1);
else ans[S[cur].id] = 0;
cur++;
}
} for(int i = 1; i <= Q; i++) printf("%d\n", ans[i]);
}
return 0;
}
线段树+离线 hdu5654 xiaoxin and his watermelon candy的更多相关文章
- HDU 5654 xiaoxin and his watermelon candy 离线树状数组 区间不同数的个数
xiaoxin and his watermelon candy 题目连接: http://acm.hdu.edu.cn/showproblem.php?pid=5654 Description Du ...
- 【HDOJ 5654】 xiaoxin and his watermelon candy(离线+树状数组)
pid=5654">[HDOJ 5654] xiaoxin and his watermelon candy(离线+树状数组) xiaoxin and his watermelon c ...
- HDU 5654 xiaoxin and his watermelon candy 离线树状数组
xiaoxin and his watermelon candy Problem Description During his six grade summer vacation, xiaoxin g ...
- 牛客练习赛53 E-老瞎眼pk小鲜肉(思维+线段树+离线)
前言 听说是线段树离线查询?? 做题做着做着慢慢对离线操作有点感觉了,不过也还没参透,等再做些题目再来讨论离线.在线操作. 这题赛后看代码发现有人用的树状数组,$tql$.当然能用树状数组写的线段树也 ...
- 数据结构(主席树):HDU 5654 xiaoxin and his watermelon candy
Problem Description During his six grade summer vacation, xiaoxin got lots of watermelon candies fro ...
- HDU 4638-Group(线段树+离线处理)
题意: 给n个编号,m个查询每个查询l,r,求下标区间[l,r]中能分成标号连续的组数(一组内的标号是连续的) 分析: 我们认为初始,每个标号为一个组(线段树维护区间组数),从左向右扫序列,当前标号, ...
- HDU 4630-No Pain No Game(线段树+离线处理)
题意: 给你n个数的序列a,q个询问,每个询问给l,r,求在下标i在[l,r]的区间任意两个数的最大公约数中的最大值 分析: 有了hdu3333经验,我们从左向右扫序列,如果当前数的约数在前面出现过, ...
- HDU 4288 Coder 【线段树+离线处理+离散化】
题意略. 离线处理,离散化.然后就是简单的线段树了.需要根据mod 5的值来维护.具体看代码了. /* 线段树+离散化+离线处理 */ #include <cstdio> #include ...
- SPOJ--K-query (线段树离线) 离线操作解决一些问题
K-query Given a sequence of n numbers a1, a2, ..., an and a number of k- queries. A k-query is a tri ...
随机推荐
- Emoji过滤
private static boolean isNotEmojiCharacter(char codePoint) { return (codePoint == 0x0) || (codePoint ...
- DataTable And DataRow
/// <summary> /// 将DataTable的字段名全部翻译为中文 /// </summary> /// <param name="table&qu ...
- SV creation order
SystemVerilog Instance Worlds When generating an UVM testbench and in particular the DUT - testbench ...
- 【sqli-labs】 less53 GET -Blind based -Order By Clause -String -Stacked injection(GET型基于盲注的字符型Order By从句堆叠注入)
http://192.168.136.128/sqli-labs-master/Less-53/?sort=1';insert into users(id,username,password) val ...
- 1 TaskQueue 实现Task 队列
class Program { static void Main(string[] args) { List<Person> list = new List<Person>() ...
- for循环提高内存访问效率的做法
今天写程序的时候突然想到一点,记录一下: 计算机内存地址是线性排列组织的,而利用for循环对高维数组结构进行遍历处理的时候,要保证最内层for循环遍历的是高维数组的最低维度,这样可以最大化利用CPU的 ...
- 通过git向github提交项目
按顺序学习 https://www.cnblogs.com/forget406/p/6045499.html#top https://blog.csdn.net/xiaoputao0903/artic ...
- Aizu - 1379 Parallel Lines
平行直线 题意:给出一些点,这些点两两相连成一条直线,问最多能连成多少条直线. 思路:暴力出奇迹!!记得当时比赛做这道题的时候一直依赖于板子,结果却限制了自己的思路,这得改.dfs直接暴力,但是需要将 ...
- UVALive 3026(KMP算法)
UVALive 3026 KMP中next[]数组的应用: 题意:给出一个字符串,问该字符串每个前缀首字母的位置和该前缀的周期. 思路:裸KMP直接上就是了: 设该字符串为str,str字符串 ...
- Python-程序的控制结构
程序的分支结构 >单分支结构 根据判断条件结果而选择不同向前路径的运行方式 if <条件>: <语句块> 代码示例: guess = eval(input()) if g ...