Loading
Loading
Build a candidate incrementally, and undo the moment it cannot work.
Explore a decision tree depth-first, extending a partial solution one choice at a time. When a partial solution cannot possibly be completed, abandon it and undo the last choice rather than continuing. The undo step is what makes this different from plain recursion, and pruning is what makes it tractable.
Choose, explore, un-choose. The un-choose is not optional bookkeeping — it is what lets one mutable buffer serve the entire tree instead of copying state at every node.
The shape, not a solution. Adapt the condition and the state to the problem in front of you.
def subsets(nums): results = [] current = [] def explore(start): # Every node of the tree is a valid subset, so record on entry. results.append(current[:]) # copy: 'current' keeps mutating for i in range(start, len(nums)): current.append(nums[i]) # choose explore(i + 1) # explore current.pop() # un-choose explore(0) return results def permutations(nums): results = [] used = [False] * len(nums) current = [] def explore(): if len(current) == len(nums): results.append(current[:]) return for i in range(len(nums)): if used[i]: continue used[i] = True current.append(nums[i]) explore() current.pop() used[i] = False # both pieces of state must be undone explore() return results| Status | Problem | Difficulty | Role |
|---|---|---|---|
| Generate Balanced Groupings#49 | Medium | Primary | |
| Count Subsets With a Target Sum#50 | Medium | Primary | |
| Keypad Spellings#131 | Medium | Primary | |
Sign in to keep a note here. It is free, and nobody else can see it.
Sign in| Feature Bundles#132 |
| Medium |
| Primary |
| Seating Orders#133 | Medium | Primary |
| Voucher Bundles#134 | Medium | Primary |
| Rooftop Beacons#135 | Hard | Primary |
| Letter Grid Trail#136 | Medium | Primary |
| Mirror Cuts#137 | Medium | Primary |