Dynamic programming is a method for solving complex problems by breaking them down into simpler subproblems, storing the results of those subproblems to avoid redundant work. It is particularly useful for optimization problems where the solution can be expressed as a combination of solutions to subproblems.
Fibonacci Sequence
The Fibonacci sequence is a series of numbers where each number is the sum of the two preceding ones, usually starting with 0 and 1. The nth Fibonacci number can be calculated using dynamic programming to avoid redundant calculations.
1 2 3 4 5 6 7 8 9 10
deffibonacci(n, memo={}): if n in memo: return memo[n] if n <= 1: return n memo[n] = fibonacci(n - 1, memo) + fibonacci(n - 2, memo) return memo[n] # Example usage: n = 10# Calculate the 10th Fibonacci number print(f"The {n}th Fibonacci number is: {fibonacci(n)}")
0-1 Knapsack Problem
The 0-1 Knapsack problem is a classic optimization problem where you have a set of items, each with a weight and a value, and a knapsack with a maximum weight capacity. The goal is to determine the maximum value that can be put in the knapsack without exceeding the weight capacity.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
defknapsack(weights, values, capacity): n = len(weights) dp = [[0for _ inrange(capacity + 1)] for _ inrange(n + 1)]
for i inrange(1, n + 1): for w inrange(capacity + 1): if weights[i - 1] <= w: dp[i][w] = max(dp[i - 1][w], dp[i - 1][w - weights[i - 1]] + values[i - 1]) else: dp[i][w] = dp[i - 1][w]
return dp[n][capacity]
# Example usage: weights = [10, 20, 30] values = [60, 100, 120] capacity = 50 print(f"The maximum value in the knapsack is: {knapsack(weights, values, capacity)}")
for i inrange(n): for j inrange(capacity, weights[i] - 1, -1): dp[j] = max(dp[j], dp[j - weights[i]] + values[i])
return dp[capacity]
Complete Knapsack Problem
Complete Knapsack problem is a variation of the 0-1 Knapsack problem where you can use an unlimited number of each item. The dynamic programming approach is similar, but we iterate through the weights in a different order.
for i inrange(n): for j inrange(weights[i], capacity + 1): dp[j] = max(dp[j], dp[j - weights[i]] + values[i])
return dp[capacity]
# Example usage: weights = [10, 20, 30] values = [60, 100, 120] capacity = 50 print(f"The maximum value in the complete knapsack is: {complete_knapsack(weights, values, capacity)}")
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
defcomplete_knapsack(weights, values, capacity): n = len(weights) dp = [[0] * (capacity +1) for _ inrange(n)]
for i inrange(n): for j inrange(1, capacity + 1): if weights[i] <= j: dp[i][j] = max(dp[i-1][j], dp[i][j - weights[i]] + values[i]) else: dp[i][j] = dp[i-1][j] return dp[n-1][capacity]
# Example usage: weights = [10, 20, 30] values = [60, 100, 120] capacity = 50 print(f"The maximum value in the complete knapsack is: {complete_knapsack(weights, values, capacity)}")