Knapsack¶
Problem¶
Given n items, each with a weight and value, and a knapsack with a weight capacity W, choose items to maximize total value without exceeding capacity. Each item can be taken at most once.
Approach¶
Classic DP. Include both the 2D tabulation (for clarity) and the space-optimized 1D version (iterate capacity backwards to avoid reusing items in the same row).
When to Use¶
Resource allocation with constraints — "maximize value under weight limit", "subset sum", "budget allocation". 0/1 variant for items used at most once. Aviation: cargo loading optimization, fuel vs payload tradeoff.
Complexity¶
| Time | O(n * W) |
| Space | O(n * W) for 2D, O(W) for 1D |
Implementation¶
knapsack ¶
0/1 Knapsack — maximize value within weight capacity.
Problem
Given n items, each with a weight and value, and a knapsack with a weight capacity W, choose items to maximize total value without exceeding capacity. Each item can be taken at most once.
Approach
Classic DP. Include both the 2D tabulation (for clarity) and the space-optimized 1D version (iterate capacity backwards to avoid reusing items in the same row).
When to use
Resource allocation with constraints — "maximize value under weight limit", "subset sum", "budget allocation". 0/1 variant for items used at most once. Aviation: cargo loading optimization, fuel vs payload tradeoff.
Complexity
Time: O(n * W) Space: O(n * W) for 2D, O(W) for 1D
knapsack ¶
Return the maximum value achievable using 1D space optimization.
knapsack([1, 3, 4, 5], [1, 4, 5, 7], 7) 9
Source code in src/algo/dp/knapsack.py
knapsack_2d ¶
Return the maximum value achievable using 2D DP table.
knapsack_2d([1, 3, 4, 5], [1, 4, 5, 7], 7) 9
Source code in src/algo/dp/knapsack.py
"""Tests for 0/1 knapsack."""
from algo.dp.knapsack import knapsack, knapsack_2d
class TestKnapsack:
def test_basic(self) -> None:
assert knapsack([1, 3, 4, 5], [1, 4, 5, 7], 7) == 9
def test_zero_capacity(self) -> None:
assert knapsack([1, 2], [10, 20], 0) == 0
def test_single_item_fits(self) -> None:
assert knapsack([5], [10], 5) == 10
def test_single_item_too_heavy(self) -> None:
assert knapsack([5], [10], 4) == 0
def test_all_items_fit(self) -> None:
assert knapsack([1, 2, 3], [6, 10, 12], 10) == 28
def test_empty(self) -> None:
assert knapsack([], [], 10) == 0
class TestKnapsack2D:
def test_matches_1d(self) -> None:
weights = [1, 3, 4, 5]
values = [1, 4, 5, 7]
assert knapsack_2d(weights, values, 7) == knapsack(weights, values, 7)
def test_basic(self) -> None:
assert knapsack_2d([2, 3, 4, 5], [3, 4, 5, 6], 5) == 7
def test_zero_capacity(self) -> None:
assert knapsack_2d([1], [5], 0) == 0
def test_no_items(self) -> None:
assert knapsack_2d([], [], 5) == 0
Implement it yourself
Run: just challenge dp knapsack
Then implement the functions to make all tests pass.
Use just study dp for watch mode.
Reveal Solution
knapsack ¶
0/1 Knapsack — maximize value within weight capacity.
Problem
Given n items, each with a weight and value, and a knapsack with a weight capacity W, choose items to maximize total value without exceeding capacity. Each item can be taken at most once.
Approach
Classic DP. Include both the 2D tabulation (for clarity) and the space-optimized 1D version (iterate capacity backwards to avoid reusing items in the same row).
When to use
Resource allocation with constraints — "maximize value under weight limit", "subset sum", "budget allocation". 0/1 variant for items used at most once. Aviation: cargo loading optimization, fuel vs payload tradeoff.
Complexity
Time: O(n * W) Space: O(n * W) for 2D, O(W) for 1D
knapsack ¶
Return the maximum value achievable using 1D space optimization.
knapsack([1, 3, 4, 5], [1, 4, 5, 7], 7) 9
Source code in src/algo/dp/knapsack.py
knapsack_2d ¶
Return the maximum value achievable using 2D DP table.
knapsack_2d([1, 3, 4, 5], [1, 4, 5, 7], 7) 9