2019牛客暑期多校训练营(第六场)D Move【暴力枚举(非二分)】
题意:
你有n件行李,有k个箱子体积相同的箱子
遵循下面的规则将行李放进箱子里面
每次都取当前最大的可以放进箱子的行李放进箱子,如果该箱子放不进任何行李那么就换一个新的箱子再按照这一条规则进行放行李
请问箱子最小的体积是多少可以放进所有行李
题目链接:
https://ac.nowcoder.com/acm/contest/886/D
题解:
答案居然没有单调性,失策了,比赛没读好题意,交了几发二分,觉得未免太简单了,还是太年轻了
来自官方题解的例子:
15 5
39 39 39 39 39 60 60 60 60 60 100 100 100 100 100
199 为一个合法的答案,但 200 不是,201 也不是。
直接从最小的答案进行枚举都可以
AC_code:
#include <bits/stdc++.h>
using namespace std;
const int maxn = 1000 + 7;
int v[maxn], n, k, used[maxn];
bool check(int x){
for(int i = 1; i <= n; i++) used[i] = 0;
for(int i = 1; i <= k; i++){
int tmp = 0;
for(int j = n; j >= 1; j--){
if(!used[j] && tmp + v[j] <= x){
used[j] = 1;
tmp += v[j];
}
}
}
for(int i = 1; i <= n; i++) if(!used[i]) return false;
return true;
}
int main(){
int T;
scanf("%d", &T);
for(int cas = 1; cas <= T; cas++){
scanf("%d%d", &n, &k);
int sum = 0;
for(int i = 1; i <= n; i++) scanf("%d", v + i), sum += v[i];
sort(v + 1, v + n + 1);
int ans = 1;
for(int i = sum / k; i <= sum; i++){
if(check(i)){
ans = i;
break;
}
}
printf("Case #%d: %d\n", cas, ans);
}
return 0;
}