题意:
给出一串序列,每次询问区间内的有多少个数的出现数量和指定的数互质。
题解:
莫队暴力的时间复杂度好像没比暴力优化多少...
#include<bits/stdc++.h> using namespace std; const int maxn=2e5+100; int a[maxn]; int cnt[maxn]; int belong[maxn]; int n,m,size,bnum,now,ans[maxn]; struct query { int l,r,id,k; }q[maxn]; int cmp (query a,query b) { return (belong[a.l]^belong[b.l]?belong[a.l]<belong[b.l]:((belong[a.l]&1?a.r<b.r:a.r>b.r))); } void add (int pos) { ++cnt[a[pos]]; } void del (int pos) { --cnt[a[pos]]; } int main () { scanf("%d%d",&n,&m); size=sqrt(n); set<int> st; bnum=n/size+(n%size>0); for (int i=1;i<=bnum;i++) for (int j=(i-1)*size;j<=i*size;j++) belong[j]=i; for (int i=1;i<=n;i++) scanf("%d",&a[i]),st.insert(a[i]); for (int i=1;i<=m;i++) { scanf("%d%d%d",&q[i].l,&q[i].r,&q[i].k); q[i].id=i; } sort(q+1,q+m+1,cmp); int l=1,r=0; for (int i=1;i<=m;i++) { int ql=q[i].l; int qr=q[i].r; while (l<ql) del(l++); while (l>ql) add(--l); while (r<qr) add(++r); while (r>qr) del(r--); //ans[q[i].id]=now; now=0; for (auto it=st.begin();it!=st.end();it++) if (__gcd(cnt[*it],q[i].k)==1&&cnt[*it]) now++; ans[q[i].id]=now; } for (int i=1;i<=m;i++) printf("%d ",ans[i]); }