【2011集训队出题】数颜色

来源:互联网 发布:网站数据库上传 编辑:程序博客网 时间:2024/04/29 11:29

Description

  墨墨购买了一套N支彩色画笔(其中有些颜色可能相同),摆成一排,你需要回答墨墨的提问。墨墨会像你发布如下指令:
  1、 Q L R代表询问你从第L支画笔到第R支画笔中共有几种不同颜色的画笔。
  2、 R P Col 把第P支画笔替换为颜色Col。
  为了满足墨墨的要求,你知道你需要干什么了吗?

Solution

这题和Dynamic len神似(这题代码也差不多),只是数据更小,n2暴力可以A。

Code

#include<iostream>#include<cstdio>#include<cstdlib>#include<algorithm>#include<cstring>#include<cmath>#define fo(i,j,k) for(int i=j;i<=k;i++)#define fd(i,j,k) for(int i=j;i>=k;i--)#define N 50001#define M 1000001#define _N 250using namespace std;int a[N];int map[M];int tot=0;struct node{    int l,r;    int z[_N],px[_N];}b[_N];bool bz[N*2];int zz[N*2];int next[N],last[N];int s[_N][N*2];int pos[N];bool cmp(int x,int y){    return next[x]<next[y];}int main(){    int n,m;    cin>>n>>m;    fo(i,0,n-1)    {        scanf("%d",&a[i]);        if(!map[a[i]]) map[a[i]]=++tot;        a[i]=map[a[i]];    }    memset(zz,-1,sizeof(zz));    fo(i,0,n-1)    {        next[i]=n;        last[i]=i;        if(zz[a[i]]<0) zz[a[i]]=i;        else        {            last[i]=zz[a[i]];            next[last[i]]=i;            zz[a[i]]=i;        }    }    int t=int(sqrt(n));    int l=0,r=t-1;    int mxn=n/t+1;    fo(i,1,n/t+1)    {        b[i].l=l,b[i].r=r;        int cnt=0;        fo(j,l,r)        {            pos[j]=i;            s[i][a[j]]++;            b[i].z[++cnt]=b[i].px[cnt]=j;        }        sort(b[i].px+1,b[i].px+r-l+2,cmp);        l=r+1;        r=min(l+t-1,n-1);    }    while(m--)    {        char ch[5];        int x,y;        scanf("%s %d %d",ch,&x,&y);        if(ch[0]=='Q')        {            x--;y--;            int ans=0;            int l=pos[x],r=pos[y];            if(l==r)            {                fo(i,x,y)                if(next[i]>y) ans++;                printf("%d\n",ans);                continue;            }            if(x>b[l].l)            {                fo(i,x,b[l].r)                if(next[i]>y) ans++;                l++;            }            if(y<b[r].r)            {                fo(i,b[r].l,y)                if(next[i]>y) ans++;                r--;            }            fo(i,l,r)            {                int ll=0,rr=b[i].r-b[i].l+1;                while(ll<rr-1)                {                    int mid=(ll+rr)/2;                    if(next[b[i].px[mid]]<=y) ll=mid;                    else rr=mid;                 }                int q;                if(next[b[i].px[rr]]<=y) q=rr;                else q=ll;                ans+=b[i].r-b[i].l-q+1;            }            printf("%d\n",ans);        }        else        {            x--;            if(!map[y]) map[y]=++tot;            y=map[y];            next[last[x]]=next[x];            int tt=pos[last[x]];            sort(b[tt].px+1,b[tt].px+b[tt].r-b[tt].l+2,cmp);            if(last[x]==x) last[next[x]]=next[x];            else last[next[x]]=last[x];            int l=pos[x],r=pos[x];            s[l][a[x]]--;            next[x]=n;            last[x]=x;            bool tf=false;            fd(i,x-1,b[l].l)            if(a[b[l].z[i-b[l].l+1]]==y)            {                last[x]=i;                next[i]=x;                tf=true;                break;            }            if(!tf)            {                fd(i,l-1,1)                if(s[i][y])                {                    fd(j,b[i].r,b[i].l)                    if(a[b[i].z[j-b[i].l+1]]==y)                    {                        last[x]=j;                        next[j]=x;                        sort(b[i].px+1,b[i].px+b[i].r-b[i].l+2,cmp);                        tf=true;                        break;                    }                    if(tf) break;                }            }            tf=false;            fo(i,x+1,b[l].r)            if(a[b[l].z[i-b[l].l+1]]==y)            {                next[x]=i;                last[i]=x;                tf=true;                break;            }            if(!tf)            {                fo(i,r+1,mxn)                if(s[i][y])                {                    fo(j,b[i].l,b[i].r)                    if(a[b[i].z[j-b[i].l+1]]==y)                    {                        next[x]=j;                        last[j]=x;                        tf=true;                        break;                    }                    if(tf) break;                }            }            a[x]=y;            s[l][y]++;            sort(b[l].px+1,b[l].px+b[l].r-b[l].l+2,cmp);        }    }}
1 0
原创粉丝点击