穷举法解决01背包利用暴力破解法(穷举法)

问题描述:给定n个重量为{w1, w2, … ,wn}、价值为{v1, v2, … ,vn}的物品和一个容量为C的背包,求这些物品中的一个最有价值的子集,且要能够装到背包中。

包的总容量15kg

物品情况

物品编号 价值 重量
1 4$ 12kg
2 2$ 2kg
3 2$ 1kg
4 1$ 1kg
5 10$ 4kg

思路:

  • 利用递归进行遍历求出各个的可能性
  • 将遍历出的结果存入int[] back = new int[N],进行缓存
  • 没存入一个back[]数组,进行遍历,将符合的题目要求allWigth[总的重量]<=15的,存入到Map<String, Integer>中
  • String表示背包情况. Integer表示总价值
  • 在存入的Map<String, Integer>的所有数据中,遍历出最大的Integer,也就是最大的价值
  • 根据Integer值,遍历出对应的String,就是背包的情况

代码

利用递归求出所有的背包情况

public class GiveBack {
     //	定义一个int数组
	int array[]=new int[1000]; 
	int N=5;
    //n为当前层数
	//求n的子集
	public  void giveback(int n){
		if(n>=N){
			for (int i = 0; i <N; i++) {
				System.out.print(array[i]);
			}
			System.out.println();
			return;
		}
		array[n]=0;
		giveback(n+1);
		array[n]=1;
		giveback(n+1);
		return;
	}
	public static void main(String[] args) {
		GiveBack giveback=new GiveBack();
		giveback.giveback(0);
	}
}

结果

所有背包情况

00000	00001	00010	00011	00100	00101	00110	00111	01000	01001	01010	01011	01100	01101	01110	01111	10000	10001	10010	10011	10100	10101	10110	10111	11000	11001	11010	11011	11100	11101	11110	11111	

最终代码

package school;

import java.util.*;

public class GiveBack3 {
    //	定义一个int数组
    int array[] = new int[1000];
    int N = 5;
    int[] value = {4, 2, 2, 1, 10};//价格
    int[] wight = {12, 2, 1, 1, 4};//体积
    int[] back = new int[N];//用来缓存所便利的可能存在的背包
    int all = 0;  //总的价值
    int allWigth = 0;//总的重量
    int count = 0;//标记遍历的次数
    Map<String, Integer> map = new HashMap<>();

    public void giveback(int n) {
        if (n >= N) {
            all = 0;//每次遍历一个循环后要置零,防止对后的影响
            allWigth = 0;
            count = 0;
            for (int i = 0; i < N; i++) {
                back[i] = array[i];
                //遍历back数组 ,所存放的背包 00100  1表示已经由背包,0表示没有
                if (back[i] == 1) {
                    all += value[i];
                    allWigth += wight[i];
                    count++;//标记遍历的次数
                } else {
                    count++;
                }
                //当遍历的次数为5和所存放的总重量小于等于15 放入Map中
                if (count == 5 && allWigth <= 15) {
                    map.put(Arrays.toString(back), all);
                }
            }
            return;
        }
        //运用递归进行调用
        array[n] = 0;
        giveback(n + 1);
        array[n] = 1;
        giveback(n + 1);
        return;
    }

    /**
     * @param map   遍历存入输入的图
     * @param value 重量
     * @return 返回value所对应的kye值
     */
    private <K, V> K getKeyByLoop(Map<K, V> map, V value) {
        for (Map.Entry<K, V> entry : map.entrySet()) {
            if (Objects.equals(entry.getValue(), value)) {
                return entry.getKey();
            }
        }
        return null;
    }

    public static void main(String[] args) {
        GiveBack3 giveback = new GiveBack3();
        giveback.giveback(0);
        //通过迭代遍历values
        Collection<Integer> values = giveback.map.values();
        Iterator<Integer> iterator = values.iterator();
        Integer temp = 0;
        while (iterator.hasNext()) {
            Integer integer = iterator.next();
            //遍历最大的values,并且赋值给temp
            if (integer > temp) {
                temp = integer;
            }
        }
        System.out.print("最大的价格\t");
        System.out.println(temp + "\t");
        //通过values值    利用getKeyByLoop函数遍历出对应的key值,也就是符合题意的而背包
        System.out.print("所选符合题意的背包\t");
        System.out.println(giveback.getKeyByLoop(giveback.map, temp));
    }
}

输出

最大的价格	15	
所选符合题意的背包	[0, 1, 1, 1, 1]

中间符合标准的,能放入背包的情况

{[0, 0, 0, 1, 0]=1, [0, 0, 0, 1, 1]=11, [0, 0, 1, 1, 0]=3, [0, 1, 0, 1, 0]=3, [1, 1, 0, 1, 0]=7, [0, 1, 1, 0, 1]=14, [0, 1, 1, 1, 0]=5, [0, 1, 0, 1, 1]=13, [0, 1, 1, 1, 1]=15, [0, 1, 0, 0, 1]=12, [0, 1, 0, 0, 0]=2, [0, 1, 1, 0, 0]=4, [0, 0, 1, 1, 1]=13, [1, 0, 0, 1, 0]=5, [1, 0, 1, 1, 0]=7, [0, 0, 0, 0, 0]=0, [1, 1, 0, 0, 0]=6, [1, 1, 1, 0, 0]=8, [0, 0, 1, 0, 1]=12, [0, 0, 1, 0, 0]=2, [0, 0, 0, 0, 1]=10, [1, 0, 1, 0, 0]=6, [1, 0, 0, 0, 0]=4}

版权声明:本文为qq_44236958原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
原文链接:https://blog.csdn.net/qq_44236958/article/details/109517507