Skip to content
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
64 changes: 64 additions & 0 deletions backtracking/inverse_coin_change.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
"""
This module finds all possible ways to combine given coin denominations
to sum up to a specified target amount using a backtracking method.
The time complexity grows exponentially based on the amount and the set of coins.
"""

from __future__ import annotations
from typing import List

Check failure on line 9 in backtracking/inverse_coin_change.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (UP035)

backtracking/inverse_coin_change.py:9:1: UP035 `typing.List` is deprecated, use `list` instead

Check failure on line 9 in backtracking/inverse_coin_change.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (I001)

backtracking/inverse_coin_change.py:8:1: I001 Import block is un-sorted or un-formatted


def inverse_coin_change(amount: int, coins: List[int]) -> List[List[int]]:

Check failure on line 12 in backtracking/inverse_coin_change.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (UP006)

backtracking/inverse_coin_change.py:12:64: UP006 Use `list` instead of `List` for type annotation

Check failure on line 12 in backtracking/inverse_coin_change.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (UP006)

backtracking/inverse_coin_change.py:12:59: UP006 Use `list` instead of `List` for type annotation

Check failure on line 12 in backtracking/inverse_coin_change.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (UP006)

backtracking/inverse_coin_change.py:12:45: UP006 Use `list` instead of `List` for type annotation
"""
Computes every possible combination of coins that add up exactly to the target amount.

Check failure on line 14 in backtracking/inverse_coin_change.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (E501)

backtracking/inverse_coin_change.py:14:89: E501 Line too long (90 > 88)
Coins can be chosen multiple times.
:param amount: The total amount to form with the coins.
:param coins: Available coin denominations.
Example 1:
>>> inverse_coin_change(4, [1, 2])
[[1, 1, 1, 1], [1, 1, 2], [2, 2]]
Example 2:
>>> inverse_coin_change(3, [2])
[]
Example 3:
>>> inverse_coin_change(0, [1, 2])
[[]]
"""
results: List[List[int]] = []

Check failure on line 32 in backtracking/inverse_coin_change.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (UP006)

backtracking/inverse_coin_change.py:32:19: UP006 Use `list` instead of `List` for type annotation

Check failure on line 32 in backtracking/inverse_coin_change.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (UP006)

backtracking/inverse_coin_change.py:32:14: UP006 Use `list` instead of `List` for type annotation

def backtrack(remaining: int, current_combo: List[int], start_index: int) -> None:

Check failure on line 34 in backtracking/inverse_coin_change.py

View workflow job for this annotation

GitHub Actions / ruff

Ruff (UP006)

backtracking/inverse_coin_change.py:34:50: UP006 Use `list` instead of `List` for type annotation

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As there is no test file in this pull request nor any test function or class in the file backtracking/inverse_coin_change.py, please provide doctest for the function backtrack

if remaining == 0:
results.append(current_combo.copy())
return
for i in range(start_index, len(coins)):
coin = coins[i]
if coin <= remaining:
current_combo.append(coin)
backtrack(remaining - coin, current_combo, i) # Allow coin reuse
current_combo.pop()

coins.sort()
backtrack(amount, [], 0)
return results


# Uncomment the lines below to accept user input
# print("Please enter the target amount:")
# target_amount = int(input())
# print("Enter the coin denominations separated by spaces:")
# coin_values = list(map(int, input().split()))
# combinations = inverse_coin_change(target_amount, coin_values)
# print(combinations)


if __name__ == "__main__":
print("Possible combinations for amount = 4 with coins [1, 2]:")
print(inverse_coin_change(4, [1, 2]))

print("\nPossible combinations for amount = 5 with coins [1, 3, 5]:")
print(inverse_coin_change(5, [1, 3, 5]))
Loading