题意:把一个m个整数的序列划分成k个连续非空的子序列,使得子序列和的最大值最小。
思路:二分。遇到最大值最小大多都二分了,让划分的子序列都不超过x,根据x来judge最终结果k个是多还是少,然后二分来调整x直到出现k个序列。
code:
#include <bits/stdc++.h>
using namespace std;typedef long long ll;
#define int long long
ll m,k,v[505],c[505];
bool judge(ll x)
{ll p=0,q=0;for (int i=0;i<m;i++){p+=v[i];if (v[i]>x) return false;if (p>x){p=v[i];q++;}}if (q>k-1) return false;return true;
}main()
{int T;scanf("%d",&T);while (T--){int s=0,len;memset(c,0,sizeof(c));scanf("%lld %lld",&m,&k);for (int i=0;i<m;i++) scanf("%lld",&v[i]),s+=v[i];int l=0,r=s,mid;while (l<r){mid=l+(r-l)/2;if (!judge(mid)) l=mid+1;else r=mid;}len=s=0;for (int i=m-1;i>=0;i--){s+=v[i];if (s>r||k-len==i+2){s=v[i];c[len++]=i;}}len=k-2;for (int i=0;i<m;i++){printf("%lld",v[i]);if (i!=m-1) printf(" ");if (len>=0&&i==c[len]) printf("/ "),len--;}puts("");}
}