分金幣
圓桌旁坐着n個人,每人有一定數量的金幣,金幣總數能被n整除。每個人可以給他左右相鄰的人一些金幣,
最終使得每個人的金幣數目相等。你的任務是求出被轉手的金幣數量的最小值。
比如,n=4,且4個人的金幣數量分別爲1,2,5,4時,只需轉移4枚金幣(第3個人給第2個人兩枚金幣,
第2個人和第4個人分別給第1個人1枚金幣)即可實現每人手中的金幣數目相等。
[輸入]
輸入包含多組數據。每組數據第一行爲整數n(n≤1 000 000),以下n行每行爲一個整數,按逆時針順序給出每個人擁有的金幣數。輸入結束標誌爲文件結束符(EOF)。
[輸出]
對於每組數據,輸出被轉手金幣數量的最小值。輸入保證這個值在64位無符號整數範圍內。
[樣例輸入]
3
100
100
100
4
1
2
5
4
[樣例輸出]
0
4
PS:
每一位的可能都是從前一位拿到一部分,然後給下一位一部分
move[i]=move[i-1]+num[i]-ave;
前一位拿到的加上自己的減去應該得到的,就是下一位的
那麼現在是從頭到尾的分金幣,
每一位上都是我要移動的金幣,
最短怎麼算?
當然是給我要移動的金幣排序,取中間值,把金幣往中間值移動,
那麼就是最短了,
有喜歡數學的可以百度看看大佬的數學推理
package 第六次模擬;
import java.util.Arrays;
import java.util.Scanner;
public class Demo6 {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
while(sc.hasNext()){
int n = sc.nextInt();
int num [] = new int [n];
int sum =0;
for (int i = 0; i < n; i++) {
num[i]=sc.nextInt();
sum+=num[i];
}
int ave = sum/n;
int move [] = new int [n];
for (int i = 1; i <n; i++) {
move[i]=move[i-1]+num[i]-ave;
}
Arrays.sort(move);
int result=0;
int mid =move[n/2];
for (int i = 0; i < move.length; i++) {
result+=Math.abs(mid-move[i]);
}
System.out.println(result);
}
}
}