描述
遥控车是在是太漂亮了,韵韵的好朋友都想来参观,所以游乐园决定举办m次车展。车库里共有n辆车,从左到右依次编号为1,2,…,n,每辆车都有一个展台。刚开始每个展台都有一个唯一的高度h[i]。主管已经列好一张单子:
L1 R1
L2 R2
…
Lm Rm
单子上的(Li,Ri)表示第i次车展将要展出编号从Li到Ri的车。
为了更加美观,展览时需要调整展台的高度,使参展所有展台的高度相等。展台的高度增加或减少1都需花费1秒时间。由于管理员只有一个人,所以只好对每个展台依次操作。每次展览结束后,展台高度自动恢复到初始高度。
请告诉管理员为了举办所有展览,他最少需要花多少时间将展台调整好。
格式
输入格式
第一行为两个正整数n、m。
第二行共n个非负整数,表示第i辆车展台的高度h[i]。
接下来m行每行2个整数Li、Ri(Li≤Ri)。
输出格式
一个正整数,调整展台总用时的最小值。
样例输入1
1
2
3
4
5
6
6 4
4 1 2 13 0 9
1 5
2 6
3 4
2 2
样例输出1
1
48
限制
各个测试点1s
提示
对于50%的数据 n≤500,m≤1000;
对于80%的数据 n≤1000,m≤100000;
对于100%的数据n≤1000,m≤200000;
答案在2^64以内。
代码
#include<cstdio>
#include<iostream>
#include<cstring>
#include<cmath>
#include<algorithm>
#define N 1005
#define ll long long
int n,cnt,rt,m;
int size[N],h[N],ans[N][N],ls[N],rs[N];
ll tot,anstot,tmp,num;
ll w[N],rnd[N],v[N],sum[N];
using namespace std;
inline int read()
{
int x=0,f=1;char ch=getchar();
while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();}
return x*f;
}
inline void update(int k)
{
size[k]=size[ls[k]]+size[rs[k]]+w[k];
sum[k]=sum[ls[k]]+sum[rs[k]]+v[k]*w[k];
}
inline void rturn(int &k)
{
int t=ls[k];ls[k]=rs[t];rs[t]=k;
update(k);update(t);k=t;
}
inline void lturn(int &k)
{
int t=rs[k];rs[k]=ls[t];ls[t]=k;
update(k);update(t);k=t;
}
inline void insert(int &k,int x)
{
if (k==0)
{
k=++cnt;
sum[k]=v[k]=x;
size[k]=w[k]=1;
rnd[k]=rand();
ls[k]=rs[k]=0;
return;
}
size[k]++;sum[k]+=x;
if (v[k]==x) w[k]++;
else if (v[k]<x)
{
insert(rs[k],x);
if (rnd[rs[k]]<rnd[k]) lturn(k);
}
else
{
insert(ls[k],x);
if (rnd[ls[k]]<rnd[k]) rturn(k);
}
}
int query(int k,int val)
{
if (val<=size[ls[k]]) return query(ls[k],val);
else if (val>size[ls[k]]+w[k])
{
tmp+=sum[ls[k]]+w[k]*v[k];
num+=size[ls[k]]+w[k];
return query(rs[k],val-size[ls[k]]-w[k]);
}
else
{
tmp+=sum[ls[k]];
num+=size[ls[k]];
return v[k];
}
}
inline void solve()
{
for (int i=1;i<=n;i++)
{
cnt=rt=tot=0;
for (int j=i;j<=n;j++)
{
tot+=h[j];
insert(rt,h[j]);
tmp=num=0;
int ave=query(rt,(j-i+2)/2);
ans[i][j]+=num*ave-tmp;
ans[i][j]+=tot-tmp-(j-i+1-num)*ave;
}
}
}
int main()
{
n=read();m=read();
for (int i=1;i<=n;i++) h[i]=read();
solve();
for (int i=1;i<=m;i++)
{
int l=read(),r=read();
anstot+=ans[l][r];
}
printf("%lld",anstot);
return 0;
}