SPOJ DQUERY 求区间内不同数的个数 主席树
这题跟HDU3333差不多吧。
离线的做法很简单,不再说了
以前做过。
主席树的做法就比较暴力了。。
什么是主席树呢。。
其实是某种称号。
在该题中的体现是可持久化的线段树。
对于一个数
如果以前没出现过
就插入到主席树中
否则就删除以前那个。
再插入主席树。
注意,所有的更新和删除都是建立了新的节点来保持其历史状态的。。
对于T[i]我们存的是从1到i区间的不同的数出现了多少个。
然后这棵树是根据T[i - 1]来建立的。
代码如下。。第一次写主席树。 几乎是照着爱将的代码写的。
不过他是倒着来插入的,我是正向来的。 无非是一个以左端点为根查询。一个以询问的右端点为根查询,
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <string>
#include <map>
#include <vector>
#include <algorithm>
#define INF 111111111
#define MAXN 33333
#define MAXM 600005
using namespace std;
int n, tot, q, a[MAXN];
int T[MAXM], lson[MAXM], rson[MAXM], val[MAXM];
int nxt[MAXN], b[MAXN];
int build(int l, int r)
{
int rt = tot++;
val[rt] = 0;
int m = (l + r) >> 1;
if(l != r)
{
lson[rt] = build(l, m);
rson[rt] = build(m + 1, r);
}
return rt;
}
int update(int rt, int pos, int v)
{
int newrt = tot++, tmp = newrt;
int l = 1, r = n;
val[newrt] = val[rt] + v;
while(l < r)
{
int m = (l + r) >> 1;
if(pos <= m)
{
lson[newrt] = tot++;
rson[newrt] = rson[rt];
newrt = lson[newrt];
rt = lson[rt];
r = m;
}
else
{
rson[newrt] = tot++;
lson[newrt] = lson[rt];
newrt = rson[newrt];
rt = rson[rt];
l = m + 1;
}
val[newrt] = val[rt] + v;
}
return tmp;
} int query(int rt, int pos)
{
int ret = 0;
int l = 1, r = n;
while(pos > l)
{
int m = (l + r) >> 1;
if(pos <= m)
{
ret += val[rson[rt]];
rt = lson[rt];
r = m;
}
else
{
l = m + 1;
rt = rson[rt];
}
}
return ret + val[rt];
}
int main()
{
while(scanf("%d", &n) != EOF)
{
tot = 0;
memset(nxt, -1, sizeof(nxt));
for(int i = 1; i <= n; i++)
{
scanf("%d", &a[i]);
b[i - 1] = a[i];
}
sort(b, b + n);
int cnt = unique(b, b + n) - b;
T[0] = build(1, n);
for(int i = 1; i <= n; i++)
{
int id = lower_bound(b, b + cnt, a[i]) - b;
if(nxt[id] == -1)
T[i] = update(T[i - 1], i, 1);
else
{
int t = update(T[i - 1], nxt[id], -1);
T[i] = update(t, i, 1);
}
nxt[id] = i;
}
scanf("%d", &q);
while(q--)
{
int l, r;
scanf("%d%d", &l, &r);
printf("%d\n", query(T[r], l));
}
}
return 0;
}
SPOJ DQUERY 求区间内不同数的个数 主席树的更多相关文章
- 区间内x的出现个数(主席树)
题目大概:求区间内x出现的次数 出题人yjy Description ZJK 给你一个长度为 n 的数列和 m 次询问,每次询问从第 l 个到第 r 个数中,数 x 出现了多少次.Input第一行一个 ...
- SPOJ 3267 D-query(离散化+主席树求区间内不同数的个数)
DQUERY - D-query #sorting #tree English Vietnamese Given a sequence of n numbers a1, a2, ..., an and ...
- HDU4622:Reincarnation(后缀数组,求区间内不同子串的个数)
Problem Description Now you are back,and have a task to do: Given you a string s consist of lower-ca ...
- HDU 4417 Super Mario(主席树求区间内的区间查询+离散化)
Super Mario Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Tota ...
- HDU 3709 Balanced Number 求区间内的满足是否平衡的数量 (数位dp)
平衡数的定义是指,以某位作为支点,此位的左面(数字 * 距离)之和 与右边相等,距离是指某位到支点的距离; 题意:求区间内满足平衡数的数量 : 分析:很好这又是常见的数位dp , 不过不同的是我们这次 ...
- D-query SPOJ - DQUERY 主席树查询区间内不同数出现的次数
我们不以权值建立主席树,而是区间端点作为值建立线段树,一个个插入a[i],我们发现这个数之前是存在的,就需要在上个版本的主席树上减去原来的位置,并加上现在的位置,这样我们在i版本的主席树,维护1-r中 ...
- SPOJ - DQUERY(区间不同数+树状数组)
链接:SPOJ - DQUERY 题意:求给定区间不同数的个数(不更新). 题解:离线+树状数组. 对所求的所有区间(l, r)根据r从小到大排序.从1-n依次遍历序列数组,在树状数组中不断更新a[i ...
- B - 低阶入门膜法 - D-query (查询区间内有多少不同的数)
题目链接:https://cn.vjudge.net/contest/284294#problem/B 题目大意:查询区间内有多少个不相同的数. 具体思路:主席树的做法,主席树的基础做法是查询区间第k ...
- SPOJ 3267 求区间不同数的个数
题意:给定一个数列,每次查询一个区间不同数的个数. 做法:离线+BIT维护.将查询按右端点排序.从左到右扫,如果该数之前出现过,则将之前出现过的位置相应删除:当前位置则添加1.这样做就保证每次扫描到的 ...
随机推荐
- new作为修饰符
new 修饰符与 new 操作符是两个概念 new 修饰符用于声明类或类的成员,表示隐藏了基类中同名的成员.而new 操作符用于实例化一个类型 new 修饰符只能用于继承类,一般用于弥补基类设计的不足 ...
- 鸟哥的linux私房菜——第12章 正则表达式与文件格式化处理
12.1什么是正则表达式 正则表达式就是处理字符串的方法,它是以行为单位来进行字符串的处理行为,正则表达式通过一些特殊符号的辅助,可以让用户轻易达到查找.删除.替换某特定字符串的处理程序. vi.gr ...
- c++清除输入缓冲区之 sync() vs ignore()
最近在写程序的时候总是不注意输入缓冲区内是否还有东西,导致出现了一些异常,调试了半天.所以来上一贴,学习注意,引以为戒! http://blog.chinaunix.net/uid-21254310- ...
- Mongodb在Windows下安装及配置 【转】
1.下载mongodb的windows版本,有32位和64位版本,根据系统情况下载,下载地址:http://www.mongodb.org/downloads 2.解压缩至E:/mongodb即可 3 ...
- bzoj 1045: [HAOI2008] 糖果传递 贪心
1045: [HAOI2008] 糖果传递 Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 1812 Solved: 846[Submit][Stat ...
- [BZOJ 1028] [JSOI2007] 麻将 【枚举+贪心判断】
题目链接:BZOJ - 1028 题目分析 枚举听的是哪种牌,再枚举成对的是哪种牌,再贪心判断: 从1到n枚举每一种牌,如果这种牌的个数小于0,就返回不合法. 将这种牌的张数 % 3, 剩下的只能和 ...
- Cocos2d-x 2.0以上版本安装方法
1,cd 到2dx根目录,MAC平台使用./create-multi-platform-projects.py 然后提示: -bash: ./create-multi-platform-projec ...
- java Clone()克隆
转自:http://www.blogjava.net/orangelizq/archive/2007/10/17/153573.html 现在Clone已经不是一个新鲜词语了,伴随着“多莉”的产生这个 ...
- Android数据存储之文件存储
首先给大家介绍使用文件如何对数据进行存储,Activity提供了openFileOutput()方法可以用于把数据输出到文件中,具体的实现过程与在J2SE环境中保存数据到文件中是一样的. public ...
- 【HDOJ】3029 Scales
CF上有道类似的,做了那个这个简单多了.思路是取模.模等于1如何处理,模等于2如何分类分类讨论后.可解.解得对数据排序后再输出. /* 3029 */ #include <iostream> ...