loj #6284. 數列分塊入門 8

#6284. 數列分塊入門 8

題目描述

給出一個長爲 nnn 的數列,以及 nnn 個操做,操做涉及區間詢問等於一個數 ccc 的元素,並將這個區間的全部元素改成 ccc。html

輸入格式

第一行輸入一個數字 nnn。ios

第二行輸入 nnn 個數字,第 i 個數字爲 aia_iai​​,以空格隔開。ui

接下來輸入 nnn 行詢問,每行輸入三個數字 lll、rrr、ccc,以空格隔開。spa

表示先查詢位於 [l,r][l,r][l,r] 的數字有多少個是 ccc,再把位於 [l,r][l,r][l,r] 的數字都改成 ccc。code

輸出格式

對於每次詢問,輸出一行一個數字表示答案。htm

樣例

樣例輸入

4
1 2 2 4
1 3 1
1 4 4
1 2 2
1 4 2

樣例輸出

1
1
0
2

數據範圍與提示

對於 100% 100\%100% 的數據,1≤n≤100000,−231≤others 1 \leq n \leq 100000, -2^{31} \leq \mathrm{others}1n100000,231​​others、ans≤231−1 \mathrm{ans} \leq 2^{31}-1ans231​​1。blog

維護區間是不是連續的相同值ip

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#define maxn 100010
using namespace std;
int n,m,block,a[maxn],tag[maxn],pos[maxn];
bool cover[maxn];
int findl(int id){return (id-1)*block+1;}
int findr(int id){return min(id*block,n);}
void reset(int id,int l,int r,int v1,int v2){
    for(int i=findl(id);i<l;i++)a[i]=v1;
    for(int i=l;i<=r;i++)a[i]=v2;
    for(int i=r+1;i<=findr(id);i++)a[i]=v1;
    cover[id]=0;
}
int count(int l,int r,int v){
    int res=0;
    for(int i=l;i<=r;i++){
        if(a[i]==v)res++;
        else a[i]=v;
    }
    return res;
}
int get(int l,int r,int v){
    if(cover[pos[l]]){
        if(tag[pos[l]]==v)return r-l+1;
        else reset(pos[l],l,r,tag[pos[l]],v);
    }
    else return count(l,r,v);
    return 0;
}
int query(int l,int r,int v){
    int res=get(l,min(findr(pos[l]),r),v);
    if(pos[l]!=pos[r])res+=get(findl(pos[r]),r,v);
    for(int i=pos[l]+1;i<=pos[r]-1;i++){
        if(cover[i]){
            if(tag[i]==v)res+=pos[l]==pos[n]?m:block;
            else tag[i]=v;
        }
        else {
            res+=count(findl(i),findr(i),v);
            cover[i]=1;
            tag[i]=v;
        }
    }
    return res;
}
int main(){
    scanf("%d",&n);
    block=sqrt(n);
    for(int i=1;i<=n;i++){
        pos[i]=(i-1)/block+1;
        scanf("%d",&a[i]);
    }
    m=n-(pos[n]-1)*block;
    int l,r,c;
    for(int i=1;i<=n;i++){
        scanf("%d%d%d",&l,&r,&c);
        printf("%d\n",query(l,r,c));
    }
    return 0;
}
相關文章
相關標籤/搜索