zoukankan      html  css  js  c++  java
  • Leetcode 377. Combination Sum IV

    377. Combination Sum IV

    • Total Accepted: 2547
    • Total Submissions: 6581
    • Difficulty: Medium

    Given an integer array with all positive numbers and no duplicates, find the number of possible combinations that add up to a positive integer target.

    Example:

    nums = [1, 2, 3]
    target = 4
    
    The possible combination ways are:
    (1, 1, 1, 1)
    (1, 1, 2)
    (1, 2, 1)
    (1, 3)
    (2, 1, 1)
    (2, 2)
    (3, 1)
    
    Note that different sequences are counted as different combinations.
    
    Therefore the output is 7.

    Follow up:
    What if negative numbers are allowed in the given array?
    How does it change the problem?
    What limitation we need to add to the question to allow negative numbers?

    思路:DP,可以自顶向下,也可以自底向上。

    假设values[i]表示的是i的被组合情况,显然有values[i]=values[i-nums[0]]+...+values[i-nums[n-1]](n=nums.size())。

    注意冗余遍历的存在,例如下面的代码就没有去除冗余的遍历:

     1 class Solution {
     2 public:
     3     int combinationSum4(vector<int>& nums, int target) {
     4         if(target<=0){
     5             return !target;
     6         }
     7         int i,n=nums.size(),res=0;
     8         for(i=0;i<n;i++){
     9             res+=combinationSum4(nums,target-nums[i]);
    10         }
    11         return res;
    12     }
    13 };

    所以可以先申请内存,记录已经计算过的数的情况。

    代码:

    自底向上:

     1 class Solution {
     2 public:
     3     int combinationSum4(vector<int>& nums, int target) {
     4         //局部域参数申请,未初始化时,可能不为0
     5         //例如
     6         //int *values=new int[target];
     7         //此时values数组的每个数的取值为任意值!
     8         vector<int> values(target+1);
     9         values[0]=1;
    10         for(int i=1;i<=target;i++){
    11             for(int j=0;j<nums.size();j++){
    12                 int temp=i-nums[j];
    13                 if(temp>=0){
    14                     values[i]=values[i]+values[temp];
    15                 }
    16             }
    17         }
    18         return values[target];
    19     }
    20 };

    自顶向下:

    values初始化为0不合适,因为values[i]==0可以意味着i不能被所给数组成,此时i已经被遍历过;也可以意味着i没有被遍历。所以设置values的初始值为0,还是不能避免大量重复的遍历操作。

     1 class Solution {
     2 public:
     3     int combinationSum4(vector<int> nums,vector<int>& values,int target) {
     4         if(target<=0){
     5             return !target;
     6         }
     7         if(values[target]==-1){
     8             values[target]=0;
     9             for(int i=0;i<nums.size();i++){
    10                 values[target]+=combinationSum4(nums,values,target-nums[i]);
    11             }
    12         }
    13         return values[target];
    14     }
    15     int combinationSum4(vector<int>& nums, int target) {
    16         //values初始化为0不合适,因为values[i]==0可以意味着i不能被所给数组成,此时i已经被遍历过
    17         //也可以意味着i没有被遍历
    18         //所以设置values的初始值为0,还是不能避免大量重复的遍历操作
    19         vector<int> values(target+1,-1);
    20         return combinationSum4(nums,values,target);
    21     }
    22 };
  • 相关阅读:
    Codeforces 787D. Legacy 线段树优化建图+最短路
    Codeforces 1051E. Vasya and Big Integers
    BZOJ3261 最大异或和
    BZOJ3531 SDOI2014 旅行
    洛谷P2468 SDOI 2010 粟粟的书架
    2018 ICPC 焦作网络赛 E.Jiu Yuan Wants to Eat
    HDU6280 From Tree to Graph
    HDU5985 Lucky Coins 概率dp
    (HDU)1334 -- Perfect Cubes (完美立方)
    (HDU)1330 -- Deck (覆盖物)
  • 原文地址:https://www.cnblogs.com/Deribs4/p/5719474.html
Copyright © 2011-2022 走看看