题解-CF121E Lucky Array

  • 题目大意

就是有两种操作:


区间里面的数加上

询问区间里有多少幸运数字

由于最大值很小,直接预处理即可

然后用树状数组维护区间这种数的个数。对于查询操作我们直接输出即可。

对于修改操作我们可以暴力扫一遍对于原来是幸运数的数先如果原数加上后为幸运数。

时间复杂度:

#include <bits/stdc++.h>
#define lowbit(x) x&(-x)
using namespace std;

const int maxn=200005;

int n,m,c[maxn],a[maxn],is[maxn],ans,ma;

inline void init(int x) {
    for ( int i=1;i<=x;i++ ) {
        int tmp=i;
        int ok=1;
        while(tmp) {
            int p=tmp%10;
            if(p!=4&&p!=7) {
                ok=0;
                break;
            }
            tmp/=10;
        }
        if(ok) is[i]=1;
    }
}

inline void add(int x,int val) {
    while(x<=n) {
        c[x]+=val;
        x+=lowbit(x);
    }
}

inline int query(int x) {
    int ret=0;
    while(x) {
        ret+=c[x];
        x-=lowbit(x);
    }
    return ret;
}

inline int read() {
    int sum=0; char ch=getchar();
    while(!isdigit(ch)) 
        ch=getchar();
    while(isdigit(ch)) 
        sum=sum*10+(ch^48),ch=getchar();
    return sum;
}

int main() {
    n=read();
    m=read();
    init(200001);
    for ( int i=1;i<=n;i++ ) {
        a[i]=read();
        if(is[a[i]]) add(i,1);
    }
    char type[11];
    for ( int i=1;i<=m;i++ ) {
        scanf("%s",type+1);
        if(type[1]==99) {
            int l=read();
            int r=read();
            printf("%d\n",query(r)-query(l-1));
        }
        else {
            int l=read();
            int r=read();
            int val=read();
            if(!val) continue;
            for ( int j=l;j<=r;j++ ) {
                if(is[a[j]]) add(j,-1);
                a[j]+=val;
                if(is[a[j]]) add(j,1);
            }
        }
    }
    return 0;
}

全部评论

相关推荐

不愿透露姓名的神秘牛友
01-05 08:26
牛客880205450号:有人鸽了,才有空缺
点赞 评论 收藏
分享
01-07 15:50
四川大学 Java
明远湖摸鱼:同年级的同学,,简历可以大一点,这个有点太密集了,实习技术可以量化的尽量量化
点赞 评论 收藏
分享
评论
1
收藏
分享

创作者周榜

更多
牛客网
牛客企业服务