天天看點

【Yandex.Algorithm 2011 Round 2, problem: (D) Powerful array】 莫隊算法

http://codeforces.com/problemset/problem/86/D

題意就是每種數字x對答案的貢獻是(x*x*出現次數),是以add函數和del函數就很明顯了。

但是由于讀入比較多,需要挂個簡單的讀入挂

代碼

#include<stdio.h>
#include<math.h>
#include<iostream>
#include<algorithm>
using namespace std;
typedef long long ll;
const int maxn  = +;
int a[maxn];
long long  sum[maxn];
int pos[maxn];
long long ans[maxn];
struct data
{
    int l,r,id;
}Q[maxn];
bool cmp(const data &a,const data &b)
{
    if(pos[a.l]==pos[b.l]) return a.r<b.r;
    return pos[a.l]<pos[b.l];
}
int L=,R=;
long long Ans=;
void add(int x)
{
    sum[a[x]]++;
    Ans+=(L*(L*sum[a[x]]-)*a[x]);//算出簡單的轉移減少常數
}
void del(int x)
{
    sum[a[x]]--;
    Ans-=(L*(L*sum[a[x]]+)*a[x]);
}
int read()
{
    ll x=;
    char c=getchar();
    while(c < '0' || c > '9')
    {
        c = getchar();
    }
    while(c >= '0' && c <= '9')
    {
        x = x *  + c - '0';
        c = getchar();
    }
    return x;
}
int main()
{
    int n,t;
    scanf("%d%d",&n,&t);
    int sz=sqrt(n);
    for(int i=;i<=n;i++)
    {
        a[i]=read();
        pos[i]=i/sz;
    }
    for(int i=;i<=t;i++)
    {
        Q[i].l=read();
        Q[i].r=read();
        Q[i].id=i;
    }
    sort(Q+,Q++t,cmp);
    for(int i=;i<=t;i++)
    {
        while(L>Q[i].l)
        {
            L--;
            add(L);
        }
        while(R<Q[i].r)
        {
            R++;
            add(R);
        }
        while(L<Q[i].l)
        {
            del(L);
            L++;
        }
        while(R>Q[i].r)
        {
            del(R);
            R--;
        }
        ans[Q[i].id]=Ans;
    }
    for(int i=;i<=t;i++)  printf("%I64d\n",ans[i]);
    return ;
}
           

友情推薦莫隊算法專題連結