Skip to content

Latest commit

 

History

History
83 lines (59 loc) · 3.72 KB

322.Coin_Change(Medium).md

File metadata and controls

83 lines (59 loc) · 3.72 KB

322. Coin Change (Medium)

Date and Time: Aug 23, 2024, 0:36 (EST)

Link: https://leetcode.com/problems/coin-change/


Question:

You are given an integer array coins representing coins of different denominations and an integer amount representing a total amount of money.

Return the fewest number of coins that you need to make up that amount. If that amount of money cannot be made up by any combination of the coins, return -1.

You may assume that you have an infinite number of each kind of coin.


Example 1:

Input: coins = [1,2,5], amount = 11

Output: 3

Explanation: 11 = 5 + 5 + 1

Example 2:

Input: coins = [2], amount = 3

Output: -1

Example 3:

Input: coins = [1], amount = 0

Output: 0


Constraints:

  • 1 <= coins.length <= 12

  • 1 <= coins[i] <= 2^{31} - 1

  • 0 <= amount <= 10^4


Walk-through:

We can use dp bottom-up method to store the value of each amount a from 0 to amount with the minimum number of coins we need to achieve for each a.

  1. initialize dp with a biggest number amount + 1 with size (amount + 1), because the base case to achieve amount = 0, we need 0 coin. So we add dp[0] = 0.

  2. Start building dp from range(1, amount + 1), we try each c from coins, if current amount a - c >= 0, we can update dp[a] = min(dp[a], 1 + dp[a-c]), which means current coin c can be used, and we update dp[a] by the recurrence relation above, we assume we take this coin c, how many coins to take for the difference, so we have 1 + dp[a-c].

  3. Finally, return the last element in dp[amount], but we need to make sure we have changed the dp[amount], otherwise, we should return -1.


Python Solution:

class Solution:
    def coinChange(self, coins: List[int], amount: int) -> int:
        # 0 1 2 3 4 5 6 7 8 9 10 11
        # 0 1 1 2 2 1 2 2 3 3 2  3
        # Build a dp table with [0, amount]
        # For a in amount, we try every denomination, if one fits, we assume we use this coin + the difference dp[a-c]
        # If a - coin >= 0 means this coin makes contribution
        # Otherwise, we don't use this coin

        # TC: O(m * n), SC: O(m), n for len(coins), m for range(amount)
        dp = [amount+1] * (amount+1)    # Set it big
        dp[0] = 0
        for a in range(1, amount+1):
            for c in coins:
                if a - c >= 0:
                    # If we take this coin + coins from prev
                    dp[a] = min(dp[a], 1 + dp[a-c])
        
        return dp[-1] if dp[-1] != amount + 1 else -1

Time Complexity: $O(n * m)$, n is len(coins), m is amount. Because each value of amount we try all the coins.
Space Complexity: $O(m)$


CC BY-NC-SABY: credit must be given to the creatorNC: Only noncommercial uses of the work are permittedSA: Adaptations must be shared under the same terms