洛谷 P4113 [HEOI2012]采花(树状数组)

 

 

又是一道莫队的模板题 

看到熟悉的 2e6 的数据量,应该也知道莫队跑步过去了,题目好不容易猜出了结论,但是却置疑他的准确

这个题目和 HH的项链 这个题比较像

同样此题也要采用树状数组来优化

对于一个区间内出现的相同的颜色,我们只计算倒数第二个所做的贡献,算法的准确性:

对于一个区间 [b.......a......a...c...a...d..A...e..a...f] (应该是不分大小写的)其中只有 A 对于答案有贡献,

  • 对于询问 [b,e] 或者 [c,e] 答案都只有 A一个;
  • 对于询问 [d,e] 答案为 0
  • 对于询问 [A,f] 答案为 1

数据不算很过分,本来以为空间会爆,如果空间爆的话,可以优化一下常数,可以将 int 改为 short

const int N=2e6+5;

    int n,m;
    int i,j,k;
    int a[N];
    struct Query 
    {
        int l,r;
        int id;
        void read(){ sdd(l,r); }
    }q[N];
    pii pos[N];
    int c[N],ans[N];
    
void add(int x,int k)
{
    for(;x<=n;x+=lowbit(x)) c[x]+=k;
}

int ask(int x)
{
    int ans=0;
    for(;x;x-=lowbit(x)) ans+=c[x];
    return ans;
}

bool cmp(Query a,Query b)
{
    return a.r<b.r;
}

signed main()
{
    //IOS;
    while(~sddd(n,k,m)){
        for(int i=1;i<=n;i++) sd(a[i]);
        for(int i=1;i<=m;i++) q[i].read(),q[i].id=i;
        sort(q+1,q+1+m,cmp);
        int j=1;
        for(int i=1;i<=m;i++){
            while(j<=q[i].r){
                if(pos[a[j]].fr==0) pos[a[j]].fr=j;
                else {
                    if(pos[a[j]].sc==0){
                        pos[a[j]].sc=j;
                        add(pos[a[j]].fr,1);
                    } else{
                        add(pos[a[j]].fr,-1);
                        add(pos[a[j]].sc,1);
                        pos[a[j]].fr=pos[a[j]].sc;
                        pos[a[j]].sc=j;
                    }
                }
                j++;
            }
            ans[q[i].id]=ask(q[i].r)-ask(q[i].l-1);
        }
        for(int i=1;i<=m;i++) pd(ans[i]);
    }
    //PAUSE;
    return 0;
}

 

已标记关键词 清除标记
相关推荐
©️2020 CSDN 皮肤主题: 酷酷鲨 设计师:CSDN官方博客 返回首页