chore: Merge pull request #650 from mandy8055/coinChangeCombMem

Added the recursive-memoized approach for coin change combination pro…
This commit is contained in:
Rak Laptudirm
2021-08-15 15:47:46 +05:30
committed by GitHub
2 changed files with 67 additions and 35 deletions

View File

@ -1,45 +1,33 @@
function change (coins, amount) {
/**
* @params {Array} coins
* @params {Number} amount
*/
export const change = (coins, amount) => {
// Create and initialize the storage
const combinations = new Array(amount + 1).fill(0)
combinations[0] = 1
// Determine the direction of smallest sub-problem
for (let i = 0; i < coins.length; i++) {
const coin = coins[i]
for (let j = coin; j < amount + 1; j++) {
combinations[j] += combinations[j - coin]
// Travel and fill the combinations array
for (let j = coins[i]; j < combinations.length; j++) {
combinations[j] += combinations[j - coins[i]]
}
}
return combinations[amount]
}
function minimumCoins (coins, amount) {
// minimumCoins[i] will store the minimum coins needed for amount i
const minimumCoins = new Array(amount + 1).fill(0)
minimumCoins[0] = 0
for (let i = 1; i < amount + 1; i++) {
minimumCoins[i] = Number.MAX_SAFE_INTEGER
}
for (let i = 1; i < amount + 1; i++) {
for (let j = 0; j < coins.length; j++) {
const coin = coins[j]
if (coin <= i) {
const subRes = minimumCoins[i - coin]
if (subRes !== Number.MAX_SAFE_INTEGER && subRes + 1 < minimumCoins[i]) {
minimumCoins[i] = subRes + 1
}
}
/**
* @params {Array} coins
* @params {Number} amount
*/
export const coinChangeMin = (coins, amount) => {
const map = { 0: 1 }
for (let i = 1; i <= amount; i++) {
let min = Infinity
for (const coin of coins) {
if (i < coin) continue
min = Math.min(min, 1 + map[i - coin])
}
map[i] = min
}
return minimumCoins[amount]
return map[amount] === Infinity ? -1 : map[amount] - 1
}
function main () {
const amount = 12
const coins = [2, 4, 5]
console.log('Number of combinations of getting change for ' + amount + ' is: ' + change(coins, amount))
console.log('Minimum number of coins required for amount :' + amount + ' is: ' + minimumCoins(coins, amount))
}
main()

View File

@ -0,0 +1,44 @@
import { change, coinChangeMin } from '../CoinChange'
test('Base Case 1', () => {
const coins = [2, 3, 5]
const amount = 0
expect(change(coins, amount)).toBe(1)
expect(coinChangeMin(coins, amount)).toBe(0)
})
test('Base Case 2', () => {
const coins = []
const amount = 100
expect(change(coins, amount)).toBe(0)
expect(coinChangeMin(coins, amount)).toBe(-1)
})
test('Test Case 1', () => {
const coins = [2, 4, 5]
const amount = 12
expect(change(coins, amount)).toBe(5)
expect(coinChangeMin(coins, amount)).toBe(3)
})
test('Test Case 2', () => {
const coins = [5, 2, 3, 7, 6, 1, 12, 11, 9, 15]
const amount = 45
expect(change(coins, amount)).toBe(12372)
expect(coinChangeMin(coins, amount)).toBe(3)
})
test('Test Case 3', () => {
const coins = [2]
const amount = 3
expect(change(coins, amount)).toBe(0)
expect(coinChangeMin(coins, amount)).toBe(-1)
})
test('Test Case 4', () => {
const coins = [3, 5, 7, 8, 9, 10, 11]
const amount = 500
expect(change(coins, amount)).toBe(35502874)
expect(coinChangeMin(coins, amount)).toBe(46)
})
test('Test Case 5', () => {
const coins = [10]
const amount = 10
expect(change(coins, amount)).toBe(1)
expect(coinChangeMin(coins, amount)).toBe(1)
})