spoj 3267. D-query 主席树求区间不同数的个数
来源:互联网 发布:黄政民在韩国地位知乎 编辑:程序博客网 时间:2024/04/30 20:27
Given a sequence of n numbers a1, a2, ..., an and a number of d-queries. A d-query is a pair (i, j) (1 ≤ i ≤ j ≤ n). For each d-query (i, j), you have to return the number of distinct elements in the subsequence ai, ai+1, ..., aj.
Input
- Line 1: n (1 ≤ n ≤ 30000).
- Line 2: n numbers a1, a2, ..., an (1 ≤ ai ≤ 106).
- Line 3: q (1 ≤ q ≤ 200000), the number of d-queries.
- In the next q lines, each line contains 2 numbers i, j representing a d-query (1 ≤ i ≤ j ≤ n).
Output
- For each d-query (i, j), print the number of distinct elements in the subsequence ai, ai+1, ..., aj in a single line.
Example
Input51 1 2 1 331 52 43 5Output323
/*求区间内不重复的数的个数。扫描数列建立可持久化线段树,第i个数若第一次出现,则在线段树中的位置i加1;若不是第一次出现,将上次出现的位置减1,在本次位置加1。对于每个询问的区间 [L,R],在第R个版本上的线段树只有前R个数,在线段树上查询位置L,对经过的区间中的和进行累计即可*/#include<stdio.h>#include<map>#define M 1000000#define N 35000using namespace std;map<int ,int >ma;int n,num,c[M],lson[M],rson[M],a[N],t[N];int build(int x,int y){ int root=num++; c[root]=0; if(x!=y) { int mid=(x+y)>>1; lson[root]=build(x,mid); rson[root]=build(mid+1,y); } return root;}int insert(int root,int k,int val){ int newroot,tp,l,r; newroot=num++; tp=num-1; c[newroot]=c[root]+val; l=1;r=n; while(l<r) { int mid=(l+r)>>1; if(k<=mid) { lson[newroot]=num++; rson[newroot]=rson[root]; newroot=lson[newroot]; root=lson[root]; r=mid; } else { rson[newroot]=num++; lson[newroot]=lson[root]; newroot=rson[newroot]; root=rson[root]; l=mid+1; } c[newroot]=c[root]+val; } return tp;}int query(int x,int y,int root,int k){ int mid=(x+y)>>1; if(x==y) return c[root]; if(k<=mid) return c[rson[root]]+query(x,mid,lson[root],k); else return query(mid+1,y,rson[root],k);}int main(){ int i,m,x,y,tmp; //freopen("a.txt","r",stdin); while(scanf("%d",&n)!=EOF) { for(i=1;i<=n;i++) scanf("%d",&a[i]); scanf("%d",&m); num=0; t[0]=build(1,n); ma.clear(); for(i=1;i<=n;i++) { if(ma.find(a[i])==ma.end()) t[i]=insert(t[i-1],i,1); else { tmp=insert(t[i-1],ma[a[i]],-1); t[i]=insert(tmp,i,1); } ma[a[i]]=i; } for(i=1;i<=m;i++) { scanf("%d%d",&x,&y); printf("%d\n",query(1,n,t[y],x)); } } return 0;}
树状数组做法:/*做法:将查询按右端点从小到大排序。从左到右扫,如果该数之前出现过,则将之前出现过的位置相应删除;当前位置则添加1。这样做就保证每次扫描到的某一位置,以该位置为右端点的区间都相应地确定了。*/#include<stdio.h>#include<algorithm>#include<string.h>#include<map>#define N 35000#define M 250000using namespace std;struct node{ int x,y,id;}b[M];int c[N],ans[M],a[N];map<int ,int >ma;bool cmp(node a,node b){ return a.y<b.y;}int lowbit(int x){ return x&(-x);}void update(int x,int val){ while(x<=N) { c[x]+=val; x+=lowbit(x); }}int sum(int x){ int s=0; while(x) { s+=c[x]; x-=lowbit(x); } return s;}int main(){ int n,i,m,pre,j; //freopen("a.txt","r",stdin); while(scanf("%d",&n)!=EOF) { for(i=1;i<=n;i++) scanf("%d",&a[i]); scanf("%d",&m); for(i=0;i<m;i++) { scanf("%d%d",&b[i].x,&b[i].y); b[i].id=i; } sort(b,b+m,cmp); pre=1; memset(c,0,sizeof(c)); for(i=0;i<m;i++) { for(j=pre;j<=b[i].y;j++) { if(ma.find(a[j])==ma.end()) update(j,1); else { update(ma[a[j]],-1); update(j,1); } ma[a[j]]=j; } ans[b[i].id]=sum(b[i].y)-sum(b[i].x-1); pre=b[i].y+1; } for(i=0;i<m;i++) printf("%d\n",ans[i]); } return 0;}
0 0
- spoj 3267. D-query 主席树求区间不同数的个数
- SPOJ D-query 主席树在线(求区间不同的数的个数)
- [spoj D-query] 主席树求区间不同数
- SPOJ D-query 区间不同数的个数 [在线主席树 or 离线树状数组]
- spoj DQUERY - D-query(区间不同数的个数 主席树 or BIT)
- spoj D-query 区间不同数个数 主席树||离线+树状数组
- SPOJ-DQUERY-主席树求区间不同数个数模板
- SPOJ D-query(区间不同的数的个数)
- SPOJ DQUERY 区间内不同数的个数 主席树
- SPOJ DQUERY 求区间内不同数的个数 主席树
- SPOJ DQUERY 求区间内不同数的个数 (主席树)
- SPOJ 3267. D-query (主席树,查询区间有多少个不相同的数)
- SPOJ - DQUERY 主席树求区间中不同数字的个数
- hdu 5919 Sequence II (主席树,求区间不同数的个数)
- hdu 5919 Sequence II(主席树,求区间不同数的个数)
- SPOJ 3267. D-query 主席树
- SPOJ DQUERY(树状数组离线处理 or 主席树 区间不同数个数)
- spoj-D-query(主席树)
- hdu1102 - Constructing Roads (求最小生成树) (Prim & Kruskal)
- Android adapter的使用
- HDU-#1875 畅通工程再续(Prim & Kruskal+并查集)
- PHP.ini修改配置下载上传文件大小
- linux下C编程规范
- spoj 3267. D-query 主席树求区间不同数的个数
- Ultimus费用控制——费用控制与报销系统的好助手
- 如何将小米3连接Eclipse
- Python新人技巧
- 附加AdventureWorks过程中的5120/948错误处理方法
- 根据各视频网站网址获取SWF链接的PHP实例仅供参考
- Android开发之Activity之间的相互调用
- hdu3874 Necklace 线段树端点更新
- SUN官方API中文版【JDK1.6】