【SDOI2009】HH的项链 线段树
题目描述
HH 有一串由各种漂亮的贝壳组成的项链。HH 相信不同的贝壳会带来好运,所以每次散步完后,他都会随意取出一段贝壳,思考它们所表达的含义。HH 不断地收集新的贝壳,因此,他的项链变得越来越长。有一天,他突然提出了一个问题:某一段贝壳中,包含了多少种不同的贝壳?这个问题很难回答……因为项链实在是太长了。于是,他只好求助睿智的你,来解决这个问题。
输入输出格式
输入格式:
第一行:一个整数N,表示项链的长度。
第二行:N 个整数,表示依次表示项链中贝壳的编号(编号为0 到1000000 之间的整数)。
第三行:一个整数M,表示HH 询问的个数。
接下来M 行:每行两个整数,L 和R(1 ≤ L ≤ R ≤ N),表示询问的区间。
输出格式:
M 行,每行一个整数,依次表示询问对应的答案。
输入输出样例
6
1 2 3 4 3 5
3
1 2
3 5
2 6
2
2
4
数据范围:
对于100%的数据,N <= 500000,M <= 500000。
---------------------------------------------------------------------------------------------------
这个数据一看就不能暴力标记什么的水过去
然后看到维护和询问的区间信息 所以很快想到了线段树
关键是维护的序列是什么呢?
我们选择维护一个1~n的序列 对每个点:为0表示此时下标表示的数不存在,为1表示此时下标表示的数存在
我们选择离线做法,先记录下每次询问 一边处理每个值 一边查询
将询问按照右端点排序,now记录当前访问到的询问
记last[i]数组 表示 i上一次出现的位置(即截止目前最后出现的位置
用一遍for循环 update贝壳的编号进入序列 即update(1,i,1); 表示现在在当前位出现
然后将上一次出现i的位置重置为0 即 update(1,last[a[i]],0); 并记下i出现的当前新位置last[a[i]]=i;
对于询问 每次从处理好的询问中 找出右端点和当前处理位置相同的询问 进行查询
怎样查询呢?
因为每一次我们只记录下了每个值最后出现的位置 以前的早已清零,所以查询一段区间中有多少的不同值就是做区间求和
于是就变成线段树的基本操作了ovo
注:1.注意线段树中查询操作的写法
2.注意开够数组
贴个代码
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cmath>
#include<cstring>
#define N 500100
#define lc p<<1
#define rc p<<1|1
using namespace std;
int n,m;
int a[N];
struct node
{
int l,r,val;
}t[N<<]; struct pu
{
int x,y,id,ans;
}q[N];
bool cmp(pu a,pu b) { return a.y<b.y; }
bool cmp1(pu a,pu b) { return a.id<b.id; } void pushup(int p){
t[p].val=t[lc].val+t[rc].val;
}
void build(int p,int l,int r)
{
t[p].l=l; t[p].r=r;
if(l==r) return;
int mid=l+r>>;
build(lc,l,mid);
build(rc,mid+,r);
pushup(p);
}
void update(int p,int x,int v)
{
if(t[p].l==t[p].r)
{
t[p].val=v;
return;
}
int mid=t[p].l+t[p].r>>;
if(x<=mid) update(lc,x,v);
else update(rc,x,v);
pushup(p);
}
int query(int p,int ql,int qr)
{
//if(t[p].l<ql||t[p].r>qr) return 0;
if(ql<=t[p].l&&t[p].r<=qr)
return t[p].val;
int ans=;
int mid=t[p].l+t[p].r>>;
if(ql<=mid) ans+=query(lc,ql,qr);
if(qr>mid) ans+=query(rc,ql,qr);
return ans;
}
int last[];
int main()
{
scanf("%d",&n);
for(int i=;i<=n;i++)
scanf("%d",&a[i]);
scanf("%d",&m);
for(int i=;i<=m;i++)
{
scanf("%d%d",&q[i].x,&q[i].y);
q[i].id=i;
}
build(,,n);
int now=;
sort(q+,q+m+,cmp);
for(int i=;i<=n;i++)
{
update(,i,);
if(last[a[i]]) update(,last[a[i]],);
last[a[i]]=i;
while(q[now].y==i)
{
q[now].ans=query(,q[now].x,q[now].y);
now++;
}
}
sort(q+,q+m+,cmp1);
for(int i=;i<=m;i++)
printf("%d\n",q[i].ans);
return ;
}
【SDOI2009】HH的项链 线段树的更多相关文章
- BZOJ 1878: [SDOI2009]HH的项链 离线树状数组
1878: [SDOI2009]HH的项链 Time Limit: 1 Sec Memory Limit: 256 MB 题目连接 http://www.lydsy.com/JudgeOnline/p ...
- [bzoj1878][SDOI2009]HH的项链_树状数组
HH的项链 bzoj-1878 SDOI-2009 题目大意:给定一个n个数的序列,m次查询.查询区间数的种类个数. 注释:$1\le n \le 5\cdot 10^4$,$1\le m\le 2\ ...
- 【BZOJ】1878: [SDOI2009]HH的项链(树状数组)
http://www.lydsy.com/JudgeOnline/problem.php?id=1878 我太弱了,看题解才过的. 一开始看到此题,我想了想在线做法,但之后觉得这个想法可能是错的:维护 ...
- P1972 [SDOI2009]HH的项链[离线+树状数组/主席树/分块/模拟]
题目背景 无 题目描述 HH 有一串由各种漂亮的贝壳组成的项链.HH 相信不同的贝壳会带来好运,所以每次散步完后,他都会随意取出一段贝壳,思考它们所表达的含义.HH 不断地收集新的贝壳,因此,他的项链 ...
- 洛谷P1972 [SDOI2009]HH的项链(树状数组)
题目链接: https://www.luogu.org/problemnew/show/P1972 题目描述: HH 有一串由各种漂亮的贝壳组成的项链.HH 相信不同的贝壳会带来好运,所以每次散步完后 ...
- [BZOJ1878][SDOI2009] HH的项链 (树状数组)
link 一道简单题. 不用可持久化. 对于统计颜色个数,可以看与其颜色一样的前一个位置. 设$las(i)$表示其与$i$颜色相等的上一个位置. 则对于二元组$(l,r)$,其答案为$\sum_{i ...
- bzoj 1878: [SDOI2009]HH的项链【树状数组】
对于一个lr,每个颜色贡献的是在(1,r)区间里出现的最右位置,所以记录一个b数组表示当前点这个颜色上一个出现的位置 然后把询问离线,按r升序排序 每次把右端点右移,把这个点在树状数组上+1,并且在当 ...
- 洛谷 P1972 [SDOI2009]HH的项链(树状数组,离线)
传送门 解题思路 因为是求区间的不同种类数,所以我们用树状数组(貌似并没有什么直接联系) (...表示到) 还是和原来一样,用s[i]来表示a[i-lowbit(i)]...a[i]的种类数. 因为有 ...
- 洛谷——P1972 [SDOI2009]HH的项链(线段树)
P1972 [SDOI2009]HH的项链 HH 有一串由各种漂亮的贝壳组成的项链.HH 相信不同的贝壳会带来好运,所以每次散步完后,他都会随意取出一段贝壳,思考它们所表达的含义.HH 不断地收集新的 ...
随机推荐
- 无法通过CTRL+空格及SHIFT+CTRL调出输入法的解决方案
打开任务管理器: 运行:CTFMON.EXE
- TFS看板的迭代规划
故事点 故事点更多体现的是用户情景或者bug的规模,采用斐波拉契数列(1,2,3,5,8,13)这样的数字表示,包含如下内容: 相对工作量 复杂度 风险和不确定性 相对工作量 下面演示一个Case来说 ...
- xtrabackup 安装
xtrabackup 安装 yum install -y perl-DBI perl-DBD-MySQL perl-Time-HiRes perl-IO-Socket-SSL perl-Dige ...
- POJ-3565 Ants---KM算法+slack优化
题目链接: https://vjudge.net/problem/POJ-3565 题目大意: 在坐标系中有N只蚂蚁,N棵苹果树,给你蚂蚁和苹果树的坐标.让每只蚂蚁去一棵苹果树, 一棵苹果树对应一只蚂 ...
- 3205: 数组做函数参数--数组元素求和1--C语言
3205: 数组做函数参数--数组元素求和1--C语言 时间限制: 1 Sec 内存限制: 128 MB提交: 178 解决: 139[提交][状态][讨论版][命题人:smallgyy] 题目描 ...
- 复选框(checkbox)、多选框
1.需求分析 可同时选中多个选项,实现全选.全不选.反选等功能. 2.技术分析 基础的HTML.CSS.JavaScript. 3.详细分析 3.1 HTML部分 图示是一个列表加底部一段文字说明,列 ...
- Webpack机制、原理简单小结
一.webpack的构成 entry 代表项目的入口 module 开发中,每一个文件可以看作一个module chunk 代码块 loader 模块转化器 plugin 扩展插件,自定义w ...
- 网络流_Edmond-Karp算法、Dinic算法
转载:网络流基础篇——Edmond-Karp算法 BY纳米黑客 网络流的相关定义: 源点:有n个点,有m条有向边,有一个点很特殊,只出不进,叫做源点. 汇点:另一个点也很特殊, ...
- php微信红包算法
微信红包算法.php /**生成红包的函数*/ function getRandMoney($totalMoney, $totalPeople=2, $miniMoney=1){ $randRemai ...
- web项目中信息显示不全
如果页面的信息加载不全: 1. 可能是SQL写的不对,查的SQL写错了会导致信息展示问题 2. 或者是分页的初始化设置 过小导致,关于分页xxxPage.java的实体类初始值的pageSize设置的 ...