|
| 1 | +# https://leetcode.com/problems/combination-sum/ |
| 2 | + |
| 3 | +from typing import List |
| 4 | + |
| 5 | +class Solution: |
| 6 | + def combinationSum1(self, candidates: List[int], target: int) -> List[List[int]]: |
| 7 | + """ |
| 8 | + [Complexity] |
| 9 | + - TC: O(n^{target/min(candidates)}) |
| 10 | + - ์ฌ๊ท ํธ์ถ ํธ๋ฆฌ์ ์ต๋ height๋ target/min(candidates) (์ค๋ณต ๊ฐ๋ฅํ๋ฏ๋ก) |
| 11 | + - ๊ฐ step์์ ์ต๋ nํ ์ฌ๊ท ํธ์ถ (for i in range(idx, n)) |
| 12 | + - SC: O(target/min(candidates)) (* res ์ ์ธ) |
| 13 | + - recursion stack = ์ต๋ O(target/min(candidates)) |
| 14 | + - combi = ์ต๋ O(target/min(candidates)) |
| 15 | +
|
| 16 | + [Approach] |
| 17 | + backtracking(idx = ํ์ฌ ๋ณด๊ณ ์๋ ์์์ ์ธ๋ฑ์ค, tot_sum = ํ์ฌ๊น์ง์ ํฉ)์ผ๋ก ์ ๊ทผํ๋ค. |
| 18 | + - base condition: tot_sum์ด target๊ณผ ๊ฐ์ผ๋ฉด res์ ์ถ๊ฐํ๊ณ , target ๋ณด๋ค ํฌ๋ฉด ์ข
๋ฃ |
| 19 | + - recursion: ํ์ฌ ๋ณด๊ณ ์๋ ์์์ ์ธ๋ฑ์ค์ ์ดํ์ ์๋ ์์๋ค์ backtracking์ผ๋ก ๊ฒ์ฌ |
| 20 | + (* "same number may be chosen from candidates" ์ด๋ฏ๋ก!) |
| 21 | + """ |
| 22 | + n = len(candidates) |
| 23 | + combi = [] |
| 24 | + res = [] |
| 25 | + |
| 26 | + def backtracking(idx, tot_sum): |
| 27 | + # base condition |
| 28 | + if tot_sum == target: |
| 29 | + res.append(combi[:]) |
| 30 | + return |
| 31 | + if tot_sum > target: |
| 32 | + return |
| 33 | + |
| 34 | + # recur |
| 35 | + for i in range(idx, n): |
| 36 | + c = candidates[i] |
| 37 | + combi.append(c) |
| 38 | + backtracking(i, tot_sum + c) |
| 39 | + combi.pop() |
| 40 | + |
| 41 | + backtracking(0, 0) |
| 42 | + |
| 43 | + return res |
| 44 | + |
| 45 | + def combinationSum(self, candidates: List[int], target: int) -> List[List[int]]: |
| 46 | + """ |
| 47 | + [Complexity] |
| 48 | + - TC: O(n^{target/min(candidates)}) |
| 49 | + - SC: O(target/min(candidates)) (* res ์ ์ธ) |
| 50 | +
|
| 51 | + [Approach] |
| 52 | + ๊ธฐ์กด backtracking ํ์ด์ ์ ๋ ฌ์ ์ถ๊ฐํด์ ์กฐ๊ธ ๋ ์ต์ ํํ ์ ์๋ค. |
| 53 | + ์ฆ, candidates๋ฅผ ์ ๋ ฌํ ํ, ๋งค ๋จ๊ณ์์ candidates[idx] > target - tot_sum ์ผ ๋๋ ์ข
๋ฃํ๋ค. |
| 54 | + ์ด๋ก ์ ์ผ๋ก ๋ณต์ก๋๋ ๋์ผํ๋(TC์ ๊ฒฝ์ฐ, ์ ๋ ฌ์ ๋๋ O(nlogn) ๋ณด๋ค ๋ฐฑํธ๋ํน์ ๋๋ O(n^m)์ด ๋ ์ง๋ฐฐ์ ), early stop์ด ๊ฐ๋ฅํด์ง๋ค. |
| 55 | + """ |
| 56 | + n = len(candidates) |
| 57 | + combi = [] |
| 58 | + res = [] |
| 59 | + |
| 60 | + candidates.sort() # -- ์ ๋ ฌ |
| 61 | + |
| 62 | + def backtracking(idx, tot_sum): |
| 63 | + # base condition |
| 64 | + if tot_sum == target: |
| 65 | + res.append(combi[:]) |
| 66 | + return |
| 67 | + if tot_sum > target or candidates[idx] > target - tot_sum: # -- optimize |
| 68 | + return |
| 69 | + |
| 70 | + # recur |
| 71 | + for i in range(idx, n): |
| 72 | + c = candidates[i] |
| 73 | + combi.append(c) |
| 74 | + backtracking(i, tot_sum + c) |
| 75 | + combi.pop() |
| 76 | + |
| 77 | + backtracking(0, 0) |
| 78 | + |
| 79 | + return res |
0 commit comments