问题描述
小兰要过生日了,好朋友妮妮想送她一个特别的礼物。妮妮找来了一个神秘的箱子,箱子的容量为 VV。她还收集了 nn 个有趣的小物件,每个物件都有一个体积 xx。
妮妮想把这些小物件中的一部分装进箱子里,当然也可以一个都不装。但是,为了增加神秘感,她希望箱子装得尽可能满,剩余的空间最小。你能帮妮妮计划一下,让她知道箱子最终的最小剩余空间吗?
输入格式
第一行共一个整数 VV,表示箱子的容量。
第二行共一个整数 nn,表示收集的小物件总数。
接下来的 nn 行,每行包含一个正整数 xx,表示第 ii 个小物件的体积。
数据范围保证: 0<n≤10000<n≤1000,1≤x,V≤10001≤x,V≤1000。
输出格式
输出一个整数,表示箱子的最小剩余空间。
样例输入
300 3 120 260 190
样例输出
40
运行限制
语言 最大运行时间 最大运行内存 C++ 2s 512M C 2s 512M Java 3s 512M Python3 4s 512M PyPy3 4s 512M
因为现在在学回溯法,于是这道题我就用的回溯法求解的,唯一不足的是,有一类样例它会超时T_T,看的题解基本都用的是动态规划,可惜自己太菜T_T。
谨以此篇,来记录一下尝试的第一道回溯法题目,只通过了90%的数据,有点遗憾;等动态规划学明白了,再来试试。
代码中的rw变量我一直误解了很久,一直以为是背包的剩余总空间,其实是还未选到的所有物品的总重量,改了好久,最后重新看了下书才发现自己之前理解错了。
import java.util.Scanner;
/**
* @ClassName 小兰的神秘礼物
* @Date 2024-09-27 22:38
* @Author Administrator
* @Description TODO
*/
public class 小兰的神秘礼物 {
static int V;
static int n;
static int x[];
static int maxv = 0;
static int rw = 0;
public static void main(String[]args) {
Scanner sc = new Scanner(System.in);
V = sc.nextInt();
n = sc.nextInt();
x = new int[n + 1];
x[0] = 0;
for(int i = 1;i < n + 1;i ++) {
x[i] = sc.nextInt();
rw += x[i];
}
dfs(1,0,rw);
System.out.println(V-maxv);
}
// rw 剩余未选物品的体积之和
public static void dfs (int i , int tw , int rw) {
if (i > n ) {
if(tw > maxv) {
maxv = tw;
}
}
else {
if (tw + x[i] <= V) {
dfs(i + 1,tw + x[i],rw - x[i]);
}
if (tw + rw - x[i] >= maxv) {
dfs(i + 1,tw,rw - x[i]);
}
}
}
}
运行结果:
后来Scanner改成io流还是会超时,等学完动态规划,再把这块补上。