Midterm 2
Agenda
Optimization in multiple dimensions
with
Uphill moves are especially probable at high temperature , but occur less frequently at low temperature.
Gradually lower : explore first, settle later. Good news: we can find global minimum, bad news it might take infinite amount of time.
Question: what is the good starting temperature and final temperature?
We still want to optimize (minimize) our multidimensional energy or cost or merit function
Find that minimizes subject to ,
The only difference is that values of the are discrete, i.e. any component of the can take a countable set of different values.
In this case, we cannot run our golden search algorithm or anything else which assumes continuous space for the .
Well, actually we can but constructing a proper constraining function will be a nightmare.
Instead, we have to find a method to search through discrete sets of all possible input values, i.e. try all possible combinations of components.
Hence, the name combinatorial optimization.
Suppose you have a backpack with the given size (volume) and a set of objects with given volumes and monetary (or sentimental) values.
Our job is to find a subset of items that still fits in the backpack and has the maximum combined value.
For simplicity, we will assume that every item occurs only once.
Our job is to maximize Subject to the following constraints
Where or , i.e. it reflects whether we take this object or not.
Recall that the component is either 0 or 1.
So, is a combination of zeros and ones .
How would we generate all possible combinations of components?
Notice that if there are objects then the number of all possible combinations is . Thus the time of the optimization grows exponentially with the number of items to chose, but we will find the global optimum.
#!/usr/bin/env python3
import numpy as np
def backpack_binary(max_capacity, values, volumes):
""" Solve backpack problem using binary coding approach."""
n = len(values)
max_value = 0
best_combination = np.zeros(n, dtype=int)
# Try all possible combinations using binary representation
# From 0 to 2^n - 1 (all possible binary numbers with n bits)
for i in range(2**n):
selected_items = np.zeros(n, dtype=int)
code = bin(i)[2:].zfill(n) # string representing bits
for i,s in enumerate(code):
selected_items[i] = 1 if s=="1" else 0
total_volume = np.sum(volumes * selected_items)
total_value = np.sum(values * selected_items)
if total_volume <= max_capacity:
if total_value > max_value:
max_value = total_value
best_combination = selected_items.copy()
return max_value, best_combination
def print_solution(values, volumes, max_capacity, max_value, selected_items):
print(f"Backpack Capacity: {max_capacity}")
print(f"Maximum Value: {max_value}")
print(f"Selected Items: {selected_items}")
print(f"{values=}")
print(f"{volumes=}")
print(f"Total number of objects: {len(values)}")
if __name__ == "__main__":
print("====== Example 1 ===========")
values1 = np.array([12, 10, 20, 15], dtype=int)
volumes1 = np.array([2, 1, 3, 2], dtype=int)
max_capacity1 = 5
max_val1, selected1 = backpack_binary(max_capacity1, values1, volumes1)
print_solution(values1, volumes1, max_capacity1, max_val1, selected1)
print("====== Example 2 ===========")
N=20
values2 = (100*np.random.uniform(size=(N))).astype(int)
volumes2 = (80*np.random.uniform(size=(N))).astype(int)
max_capacity2 = 50
import time
t0 = time.time()
max_val2, selected2 = backpack_binary(max_capacity2, values2, volumes2)
print_solution(values2, volumes2, max_capacity2, max_val2, selected2)
print(f"Execution time: {time.time() - t0}")For realization of this algorithm, have a look at the backpack_binaray.py