题目

类型:Bit Manipulation
image.png

解题思路

image.png

代码

  1. package bitManipulation;
  2. import java.util.*;
  3. public class ShoppingOffers {
  4. Map<List<Integer>, Integer> memo = new HashMap<>();
  5. public int shoppingOffers(List<Integer> price, List<List<Integer>> special, List<Integer> needs) {
  6. int n = price.size();
  7. // 过滤不需要计算的大礼包,只保留需要计算的大礼包
  8. List<List<Integer>> filterSpecial = new ArrayList<>();
  9. for (List<Integer> sp : special) {
  10. int totalCount = 0, totalPrice = 0;
  11. for (int i = 0; i < n; ++i) {
  12. totalCount += sp.get(i);
  13. totalPrice += sp.get(i) * price.get(i);
  14. }
  15. if (totalCount > 0 && totalPrice > sp.get(n)) {
  16. filterSpecial.add(sp);
  17. }
  18. }
  19. return dfs(price, special, needs, filterSpecial, n);
  20. }
  21. // 记忆化搜索计算满足购物清单所需花费的最低价格
  22. public int dfs(List<Integer> price, List<List<Integer>> special, List<Integer> curNeeds, List<List<Integer>> filterSpecial, int n) {
  23. if (!memo.containsKey(curNeeds)) {
  24. int minPrice = 0;
  25. for (int i = 0; i < n; ++i) {
  26. minPrice += curNeeds.get(i) * price.get(i); // 不购买任何大礼包,原价购买购物清单中的所有物品
  27. }
  28. for (List<Integer> curSpecial : filterSpecial) {
  29. int specialPrice = curSpecial.get(n);
  30. List<Integer> nxtNeeds = new ArrayList<Integer>();
  31. for (int i = 0; i < n; ++i) {
  32. if (curSpecial.get(i) > curNeeds.get(i)) { // 不能购买超出购物清单指定数量的物品
  33. break;
  34. }
  35. nxtNeeds.add(curNeeds.get(i) - curSpecial.get(i));
  36. }
  37. if (nxtNeeds.size() == n) { // 大礼包可以购买
  38. minPrice = Math.min(minPrice, dfs(price, special, nxtNeeds, filterSpecial, n) + specialPrice);
  39. }
  40. }
  41. memo.put(curNeeds, minPrice);
  42. }
  43. return memo.get(curNeeds);
  44. }
  45. public static void main(String[] args) {
  46. ShoppingOffers shoppingOffers = new ShoppingOffers();
  47. List<Integer> price = Arrays.asList(2,5);
  48. List<Integer> needs = Arrays.asList(3,2);
  49. List<List<Integer>> special = Arrays.asList(Arrays.asList(3, 0, 5), Arrays.asList(1, 2, 10));
  50. System.out.println(shoppingOffers.shoppingOffers(price, special, needs));
  51. }
  52. }