Description
有n个小朋友坐成一圈,每人有ai个糖果。每人只能给左右两人传递糖果。每人每次传递一个糖果代价为1。
Input
小朋友个数n 下面n行 ai
Output
求使所有人获得均等糖果的最小代价。
Sample Input
4
1
2
5
4
Sample Output
4
数据规模
30% n<=1000
100% n<=1000000
说难又不难,我对数学题没什么感觉啊
首先,均分纸牌都做过吧(什么,没做过!?百度NOIP2002均分纸牌)
这个只是环形而已,为了把它变成环形,我们要知道a1给了an多少
不妨设a1给an的糖果数为k
那我们的答案就是ans=k+|a1-k-average|+|a1+a2-k-2*average|+|a1+a2+a3-k-3*average|+......+|a1+a2+a3+......+a(n-1)-k-(n-1)*average|
前面的k可以看成|0-k|
所以我求的就是|0-k|+|a1-k-average|+|a1+a2-k-2*average|+|a1+a2+a3-k-3*average|+......+|a1+a2+a3+......+a(n-1)-k-(n-1)*average|的最小值
这个就是一道经典的奥赛题了,k取中位数时最小,排个序就行了
1 const 2 maxn=1000010; 3 var 4 b:array[0..maxn]of int64; 5 a:array[0..maxn]of longint; 6 n:longint; 7 x,k,ans:int64; 8 9 procedure init; 10 var 11 i:longint; 12 begin 13 read(n); 14 for i:=1 to n do 15 begin 16 read(a[i]); 17 inc(x,a[i]); 18 end; 19 x:=x div n; 20 end; 21 22 procedure sort(l,r:longint); 23 var 24 i,j:longint; 25 t,y:int64; 26 begin 27 i:=l; 28 j:=r; 29 y:=b[(l+r)>>1]; 30 repeat 31 while b[i]<y do 32 inc(i); 33 while b[j]>y do 34 dec(j); 35 if i<=j then 36 begin 37 t:=b[i]; 38 b[i]:=b[j]; 39 b[j]:=t; 40 inc(i); 41 dec(j); 42 end; 43 until i>j; 44 if i<r then sort(i,r); 45 if j>l then sort(l,j); 46 end; 47 48 procedure work; 49 var 50 i:longint; 51 begin 52 b[1]:=0; 53 for i:=2 to n do 54 b[i]:=b[i-1]+a[i-1]-x; 55 sort(1,n); 56 k:=b[(n+1)>>1]; 57 for i:=1 to n do 58 inc(ans,abs(b[i]-k)); 59 write(ans); 60 end; 61 62 begin 63 init; 64 work; 65 end.