小B的询问

时间:2023-03-10 06:20:05
小B的询问

OJ题号:BZOJ3781、洛谷2709

思路:

根据平方和公式,$(a+b)^2=a^2+2ab+b^2$,即当$c_i$增加$1$时,新的答案增加$2C_i+1$,减少时亦同。莫队求解即可。

 #include<cstdio>
#include<cctype>
#include<cmath>
#include<algorithm>
inline int getint() {
char ch;
while(!isdigit(ch=getchar()));
int x=ch^'';
while(isdigit(ch=getchar())) x=(((x<<)+x)<<)+(ch^'');
return x;
}
int base;
struct Que {
int l,r,id;
bool operator < (const Que &x) const {
return (r/base<x.r/base)?true:((r/base==x.r/base)?(l<x.l):false);
}
};
const int K=;
int cnt[K]={},Ans=;
inline void inc(const int x) {
Ans+=cnt[x]<<|;
cnt[x]++;
}
inline void dec(const int x) {
cnt[x]--;
Ans-=cnt[x]<<|;
}
int main() {
int n=getint(),m=getint();getint();
base=(int)sqrt(n);
int a[n];
for(int i=;i<n;i++) a[i]=getint();
Que q[m];
for(int i=;i<m;i++) {
q[i].l=getint()-;
q[i].r=getint()-;
q[i].id=i;
}
std::sort(&q[],&q[m]);
int ans[m];
for(int i=,l=,r=-;i<m;i++) {
while(r<q[i].r) inc(a[++r]);
while(r>q[i].r) dec(a[r--]);
while(l<q[i].l) dec(a[l++]);
while(l>q[i].l) inc(a[--l]);
ans[q[i].id]=Ans;
}
for(int i=;i<m;i++) printf("%d\n",ans[i]);
return ;
}