动态规划背包问题总结

Posted 知道什么是码怪吗?

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了动态规划背包问题总结相关的知识,希望对你有一定的参考价值。

常用算法代码模板总结

目录

01背包问题

完全背包问题

多重背包问题

分组背包问题


01背包问题

 java题解

朴素做法

import java.util.Scanner;

public class Main 

    public static void main(String[] args) 
        Scanner input = new Scanner(System.in);
        int n = input.nextInt();//n件物品
        int m = input.nextInt();//m个体积

        int[] v = new int[1010];//每件物品的体积
        int[] w = new int[1010];//每件物品的价值

        int[][] result = new int[1010][1010];//result[i][j]表示从前i件物品中选总体积为j的物品的最大价值

        for (int i = 1; i <= n; i++) //接收数据
            v[i] = input.nextInt();//体积
            w[i] = input.nextInt();//价值
        
/*-----------------------------------------------------*/
        for (int i = 1; i <= n; i++) 
            for (int j = 1; j <= m; j++) 
                result[i][j] = result[i - 1][j];
                if (j >= v[i])//如果当前背包的体积大于了这件物品的体积,取一次max看是放入这件物品后总价值大还是不放价值大
                    result[i][j] = Math.max(result[i][j], result[i - 1][j - v[i]] + w[i]);
            
        
/*-----------------------------------------------------*/
        System.out.println(result[n][m]);

    


滚动数组空间优化

import java.util.Scanner;

public class Main 

    public static void main(String[] args) 
        Scanner input = new Scanner(System.in);
        int n = input.nextInt();//n件物品
        int m = input.nextInt();//m个体积

        int[] v = new int[1010];//每件物品的体积
        int[] w = new int[1010];//每件物品的价值

        int[] result = new int[1010];//result[i]表示体积为选体积为i的最大价值,会随着循环的遍历不停刷新

        for (int i = 1; i <= n; i++) //接收数据
            v[i] = input.nextInt();//体积
            w[i] = input.nextInt();//价值
        
/*-----------------------------------------------------*/
        for (int i = 1; i <= n; i++) 
            for (int j = m; j >= v[i]; j--) //滚动数组,从大到小的遍历,比j小的result值相当于i-1层的最大价值
                result[j] = Math.max(result[j], result[j - v[i]] + w[i]);
            
        
/*-----------------------------------------------------*/
        System.out.println(result[m]);

    


完全背包问题

 朴素做法

import java.util.Scanner;

public class Main 

    public static void main(String[] args) 
        Scanner input = new Scanner(System.in);
        int n = input.nextInt();//n件物品
        int m = input.nextInt();//m个体积

        int[] v = new int[1010];//每件物品的体积
        int[] w = new int[1010];//每件物品的价值
        int[][] result = new int[1010][1010];//记录结果

        for (int i = 1; i <= n; i++) //接收数据
            v[i] = input.nextInt();//体积
            w[i] = input.nextInt();//价值
        
/*-----------------------------------------------------*/
        for (int i = 1; i <= n; i++) 
            for (int j = 0; j <= m; j++) 
                for (int k = 0; k * v[i] <= j; k++) 
                    result[i][j] = Math.max(result[i][j], result[i - 1][j - k * v[i]] + k * w[i]);
                
            
        
/*-----------------------------------------------------*/
        System.out.println(result[n][m]);


    

 时间空间优化

import java.util.Scanner;

public class Main 

    public static void main(String[] args) 
        Scanner input = new Scanner(System.in);
        int n = input.nextInt();//n件物品
        int m = input.nextInt();//m个体积

        int[] v = new int[1010];//每件物品的体积
        int[] w = new int[1010];//每件物品的价值
        int[] result = new int[1010];

        for (int i = 1; i <= n; i++) //接收数据
            v[i] = input.nextInt();//体积
            w[i] = input.nextInt();//价值
        
/*-----------------------------------------------------*/
        for (int i = 1; i <= n; i++) 
            for (int j = v[i]; j <= m; j++) //因为当j小于v[i]的时候,放不进去,可以不用遍历
                result[j]=Math.max(result[j],result[j-v[i]]+w[i]);
            
        
/*-----------------------------------------------------*/
        System.out.println(result[m]);


    

多重背包问题

朴素做法 

import java.util.Scanner;

public class Main 

    public static int size = 1010;

    public static void main(String[] args) 
        Scanner input = new Scanner(System.in);
        int n = input.nextInt();
        int m = input.nextInt();

        int[][] dp = new int[size][size];
        int[] v = new int[size];
        int[] w = new int[size];
        int[] c = new int[size];
        for (int i = 1; i <= n; i++) 
            v[i] = input.nextInt();
            w[i] = input.nextInt();
            c[i] = input.nextInt();
        
/*-----------------------------------------------------*/
        for (int i = 1; i <= n; i++) 
            for (int j = 0; j <= m; j++) 
                for (int k = 0; k <= c[i]; k++) 
                    if (k * v[i] <= j)
                        dp[i][j] = Math.max(dp[i][j], dp[i - 1][j - k * v[i]] + k * w[i]);
                
            
        
/*-----------------------------------------------------*/
        System.out.println(dp[n][m]);
    

时间空间优化

优化方式和01背包类似

import java.util.Scanner;

public class Main 

    public static int size = 1010;

    public static void main(String[] args) 
        Scanner input = new Scanner(System.in);
        int n = input.nextInt();
        int m = input.nextInt();

        int[] dp = new int[size];
        int[] v = new int[size];
        int[] w = new int[size];
        int[] c = new int[size];
        for (int i = 1; i <= n; i++) 
            v[i] = input.nextInt();
            w[i] = input.nextInt();
            c[i] = input.nextInt();
        
/*-----------------------------------------------------*/
        for (int i = 1; i <= n; i++) 
            for (int j = m; j >= v[i]; j--) 
                for (int k = 0; k <= c[i]; k++) 
                    if (k * v[i] <= j) 
                        dp[j] = Math.max(dp[j], dp[j - k * v[i]] + k * w[i]);
                    
                
            
        
/*-----------------------------------------------------*/
        System.out.println(dp[m]);
    


分组背包问题

 朴素做法

import java.util.Scanner;

public class Main 

    public static int size = 1010;

    public static void main(String[] args) 
        Scanner input = new Scanner(System.in);
        int n = input.nextInt();
        int m = input.nextInt();

        int[][] dp = new int[size][size];
        int[] c = new int[size];
        int[][] v = new int[size][size];//v[i][j]表示第i组第j件物品的体积
        int[][] w = new int[size][size];//w[i][j]表示第i组第j件物品的价值
        for (int i = 1; i <= n; i++) 
            c[i] = input.nextInt();
            for (int j = 0; j < c[i]; j++) 
                v[i][j] = input.nextInt();
                w[i][j] = input.nextInt();
            
        
/*-----------------------------------------------------*/
        for (int i = 1; i <= n; i++) 
            for (int j = 0; j <= m; j++) 
                dp[i][j] = dp[i - 1][j];//如果不选当前种类的物品
                for (int k = 0; k < c[i]; k++) 
                    if (v[i][k] <= j)
                        dp[i][j] = Math.max(dp[i][j], dp[i - 1][j - v[i][k]] + w[i][k]);
                
            
        
/*-----------------------------------------------------*/
        System.out.println(dp[n][m]);
    

空间优化

import java.util.Scanner;

public class Main 

    public static int size = 1010;

    public static void main(String[] args) 
        Scanner input = new Scanner(System.in);
        int n = input.nextInt();
        int m = input.nextInt();

        int[] dp = new int[size];
        int[] c = new int[size];
        int[][] v = new int[size][size];//v[i][j]表示第i组第j件物品的体积
        int[][] w = new int[size][size];//w[i][j]表示第i组第j件物品的价值
        for (int i = 1; i <= n; i++) 
            c[i] = input.nextInt();
            for (int j = 0; j < c[i]; j++) 
                v[i][j] = input.nextInt();
                w[i][j] = input.nextInt();
            
        
/*-----------------------------------------------------*/
        for (int i = 1; i <= n; i++) 
            for (int j = m; j >= 0; j--) 
                for (int k = 0; k < c[i]; k++) 
                    if (v[i][k] <= j)
                        dp[j] = Math.max(dp[j], dp[j - v[i][k]] + w[i][k]);
                
            
        
/*-----------------------------------------------------*/
        System.out.println(dp[m]);
    

以上是关于动态规划背包问题总结的主要内容,如果未能解决你的问题,请参考以下文章

急!动态规划 多人背包问题

动态规划之背包问题

动态规划--01背包问题

动态规划 01背包问题

动态规划-背包问题

动态规划-背包问题