70分求助
  • 板块P1489 猫狗大战
  • 楼主KKKZOZ
  • 当前回复0
  • 已保存回复0
  • 发布时间2023/1/13 21:45
  • 上次更新2023/10/24 04:22:19
查看原帖
70分求助
60925
KKKZOZ楼主2023/1/13 21:45

求助各位大佬看下我的思路哪里有问题(能举个反例就更好了,想了半天没想出来)

我想的是二维01背包+装箱问题

假设给了 nn 个数,分别为aia_i,和为 sumsum

m=n+12m=\dfrac{n+1}{2}tar=sum2tar=\dfrac{sum}{2}

则问题可以转换为: 物品拥有二维体积,第一维体积都为1,第二维体积为 aia_i,价值为 aia_i

背包一维容量为 mm,二维容量为 tartar,问这个背包能装到的最大价值为多少

主体代码为

public static void main(String[] args) throws IOException {
        n = nextInt();
        m = (n+1)/2;
        a = new int[n + 1];
        int sum=0;
        for(int i=1;i<=n;i++){
            a[i]=nextInt();
            sum += a[i];
        }
        int tar = (sum+1)/2;
        f = new int[m+1][tar+1];

        for(int i=1;i<=n;i++)
            for(int j=m;j>=1;j--)
                for(int k=tar;k>=a[i];k--){
                    f[j][k]=Math.max(f[j][k],f[j-1][k-a[i]]+a[i]);
                }

        int ans1=f[m][tar],ans2 = sum-ans1;
        cout.println(Math.min(ans1,ans2)+" "+Math.max(ans1,ans2));
        cout.flush();
    } // End of main

完整代码

import java.io.*;

public class Main {

    static int status;
    static BufferedReader buf = new BufferedReader(new InputStreamReader(System.in));
    static BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));
    static PrintWriter cout = new PrintWriter(bw);
    static StreamTokenizer st = new StreamTokenizer(buf);

    public static int nextInt() throws IOException {
        status = st.nextToken();
        return (int) st.nval;
    }

    public static long nextLong() throws IOException {
        status = st.nextToken();
        return (long) st.nval;
    }

    public static String nextString() throws IOException {
        status = st.nextToken();
        return st.sval;
    }

    static int n, m, k;
    static int[] a;
    static int[][] f;

    public static void main(String[] args) throws IOException {
        n = nextInt();
        m = (n+1)/2;
        a = new int[n + 1];
        int sum=0;
        for(int i=1;i<=n;i++){
            a[i]=nextInt();
            sum += a[i];
        }
        int tar = (sum+1)/2;
        f = new int[m+1][tar+1];

        for(int i=1;i<=n;i++)
            for(int j=m;j>=1;j--)
                for(int k=tar;k>=a[i];k--){
                    f[j][k]=Math.max(f[j][k],f[j-1][k-a[i]]+a[i]);
                }

        int ans1=f[m][tar],ans2 = sum-ans1;
        cout.println(Math.min(ans1,ans2)+" "+Math.max(ans1,ans2));
        cout.flush();
    } // End of main
}
2023/1/13 21:45
加载中...