【Codeforces323C】Two permutations

来源:互联网 发布:免流量软件下载 编辑:程序博客网 时间:2024/06/07 15:28

题意:
给你两个长度为n1n排列,多次询问在第一个排列的[l1,r1]和第二个排列的[l2,r2]同时出现的数有多少个。

转为一个序列的问题后就是一道主席树模板题了。

#include <bits/stdc++.h>#define gc getchar()#define mid (l+r>>1)#define N 2000009#define M 40000009using namespace std;int lson[M],rson[M],sum[M],root[N];int n,a[N],pos[N],Q,ans,cnt;int read(){    int x=1;    char ch;    while (ch=gc,ch<'0'||ch>'9') if (ch=='-') x=-1;    int s=ch-'0';    while (ch=gc,ch>='0'&&ch<='9') s=s*10+ch-'0';    return s*x;}void ins(int &cur,int l,int r,int x,int last){    cur=++cnt;    lson[cur]=lson[last];    rson[cur]=rson[last];    sum[cur]=sum[last]+1;    if (l==r) return;    if (x<=mid) ins(lson[cur],l,mid,x,lson[last]);    else ins(rson[cur],mid+1,r,x,rson[last]);}int qry(int cur,int l,int r,int L,int R){    if (L<=l&&R>=r) return sum[cur];    int ret=0;    if (L<=mid) ret+=qry(lson[cur],l,mid,L,R);    if (R>mid) ret+=qry(rson[cur],mid+1,r,L,R);    return ret;}int f(int x){    return (x-1+ans)%n+1;}int main(){    n=read();    for (int i=1;i<=n;i++) pos[read()]=i;    for (int i=1;i<=n;i++) a[i]=pos[read()];    for (int i=1;i<=n;i++) ins(root[i],1,n,a[i],root[i-1]);    Q=read();    while (Q--)    {        int x=f(read()),y=f(read()),z=f(read()),w=f(read());        if (x>y) swap(x,y);        if (z>w) swap(z,w);        printf("%d\n",ans=qry(root[w],1,n,x,y)-qry(root[z-1],1,n,x,y));        ans++;    }    return 0;}