[Codeforces1254B]Send Boxes to Alice

题意

n n n盒排成一列的糖果盒,第 i i i盒有 a i a_i ai个糖果

每次可以取出某一盒一颗糖果放到相邻的糖果盒里

问使得所有盒子的里的糖果数均能被某个 k ( k > 1 ) k(k>1) k(k>1)整除的最少移动次数


题解

设糖果总数的 S u m Sum Sum(显然 S u m = 1 Sum=1 Sum=1无解)

符合条件的 k k k一定满足 k ∣ S u m k\mid Sum kSum

考虑对于一个 k k k如何求解最少的移动次数

首先肯定要将所有的 a i a_i ai k k k取余

对于一个 a i a_i ai可以将 a i a_i ai颗糖果全部向后挪,于是 a i + 1 = ( a i + 1 + a i ) m o d    k a_{i+1}=(a_{i+1}+a_i)\mod k ai+1=(ai+1+ai)modk

也可以从后面挪 k − a i k-a_i kai颗糖果到 a i a_i ai上,于是 a i + 1 = a i + 1 − ( k − a i ) ≡ a i + 1 + a i m o d    k a_{i+1}=a_{i+1}-(k-a_i)\equiv a_{i+1}+a_i \mod k ai+1=ai+1(kai)ai+1+aimodk

S i = ∑ k = 1 i a i m o d    k S_i=\sum_{k=1}^ia_i \mod k Si=k=1iaimodk,那么 A n s = ∑ i = 1 n min ⁡ ( S i , k − S i ) Ans=\sum_{i=1}^n\min(S_i,k-S_i) Ans=i=1nmin(Si,kSi)

通过上面可以发现如果如果 k 1 ∣ S u m , k 2 ∣ S u m k_1\mid Sum,k_2\mid Sum k1Sum,k2Sum,且 k = k 1 k 2 ∣ S u m k=k_1k_2\mid Sum k=k1k2Sum

那么 k k k的答案一定不会比 k 1 , k 2 k_1,k_2 k1,k2优,所以只需要枚举 S u m Sum Sum的质因子即可

题目当中 S u m ≤ 1 0 12 Sum\le10^{12} Sum1012,而 2 × 3 × 5 × … × 37 > 1 0 12 2\times3\times5\times\ldots\times37>10^{12} 2×3×5××37>1012,所以计算次数不会太多

时间复杂度为 O ( n × S u m O(n\times Sum O(n×Sum质因子个数 + S u m ) +\sqrt{Sum}) +Sum )

using ll=long long;
inline ll Calc(ll p){
	ll Cnt=0,Tmp=0;
	for(int i=1;i<=n;++i)
		Cnt=(Cnt+a[i])%p,Tmp+=min(Cnt,p-Cnt);
	return Tmp;
}
inline void Sol(){
	scanf("%d",&n);
	for(int i=1;i<=n;++i)
		scanf("%d",a+i),Sum+=a[i];
	if(Sum<2)
		return(void)puts("-1");
	Ans=-1ull>>1;
	for(int i=2;(ll)i*i<=Sum;++i)
		if(Sum%i==0){
			while(Sum%i==0)Sum/=i;
			Ans=min(Ans,Calc(i));
		}
	if(Sum>1)
		Ans=min(Ans,Calc(Sum));
	printf("%d\n",Ans);
}
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值