首页 > 代码库 > 洛谷 P3674 小清新人渣的本愿 [莫队 bitset]

洛谷 P3674 小清新人渣的本愿 [莫队 bitset]

传送门

题意:

给你一个序列a,长度为n,有Q次操作,每次询问一个区间是否可以选出两个数它们的差为x,或者询问一个区间是否可以选出两个数它们的和为x,或者询问一个区间是否可以选出两个数它们的乘积为x ,这三个操作分别为操作1,2,3


 

题面太强啦!!!

感觉就是莫队,想了一下分块不好搞更坚定了莫队的信念

$a-b=x$,$a=x+b$,放在权值数组上就是b右移x位,$bitset$大法好

加法同理

乘法,总共就$\sqrt{N}$个约数....

#include <iostream>#include <cstdio>#include <cstring>#include <algorithm>#include <cmath>#include <bitset>using namespace std;typedef long long ll;const int N=1e5+5, M=2e5+5;inline ll read(){    char c=getchar();ll x=0,f=1;    while(c<0||c>9){if(c==-)f=-1; c=getchar();}    while(c>=0&&c<=9){x=x*10+c-0; c=getchar();}    return x*f;}int n, Q, a[N], op, l, r, x;int block, m, pos[N];struct meow{    int l, r, x, type, qid;    bool operator <(const meow &a) const {return pos[l]==pos[a.l] ? r<a.r : pos[l]<pos[a.l];}}q[N];int ans[N];struct Meow{    bitset<M> a, b, c;    int cou[N];    inline void add(int v) {        cou[v]++;        if(cou[v]==1) a[v]=1, b[v+N]=1, c[-v+N]=1;    }    inline void del(int v) {        cou[v]--;        if(cou[v]==0) a[v]=0, b[v+N]=0, c[-v+N]=0;    }    int Que(int type, int x) { //printf("Que %d %d\n",type,x);        int ans=0;        if(type==1) {            if( (a & (a<<x)).any() ) ans=1;        }else if(type==2) {            if( (b & (c<<x)).any() ) ans=1;        }else {            int m=sqrt(x);            for(int i=1; i<=m; i++) if(x%i == 0)                 if(cou[i] && cou[x/i]) {ans=1; break;}        }        return ans;    }}A;void modui(){    int l=1, r=0;    for(int i=1; i<=Q; i++){        while(r<q[i].r) r++, A.add(a[r]);        while(r>q[i].r) A.del(a[r]), r--;        while(l<q[i].l) A.del(a[l]), l++;        while(l>q[i].l) l--, A.add(a[l]);        ans[q[i].qid]= A.Que(q[i].type, q[i].x);    }}int main(){//    freopen("in","r",stdin);    n=read(); Q=read();    block=sqrt(n); m=(n-1)/block+1;    for(int i=1; i<=n; i++) a[i]=read(), pos[i]=(i-1)/block+1;    for(int i=1; i<=Q; i++)         op=read(), l=read(), r=read(), x=read(), q[i]=(meow){l, r, x, op, i};    sort(q+1, q+1+Q);    modui();    for(int i=1; i<=Q; i++) puts(ans[i] ? "hana" : "bi");}

 

洛谷 P3674 小清新人渣的本愿 [莫队 bitset]