com2014-template/Workshop - 4 (TSP SA).ipynb

1027 lines
167 KiB
Plaintext

{
"cells": [
{
"cell_type": "markdown",
"metadata": {},
"source": [
"**Make sure you run this at the begining**"
]
},
{
"cell_type": "code",
"execution_count": 1,
"metadata": {},
"outputs": [],
"source": [
"import os\n",
"import sys\n",
"import math\n",
"import numpy as np\n",
"import matplotlib.pyplot as plt\n",
"\n",
"# Append template path to sys path\n",
"sys.path.append(os.getcwd() + \"/template\") "
]
},
{
"cell_type": "code",
"execution_count": 2,
"metadata": {},
"outputs": [],
"source": [
"from utils.load_data import load_data\n",
"from utils.load_data import log\n",
"from utils.visualize_tsp import plotTSP\n",
"from utils.tsp import TSP\n",
"from utils.tsp import TSP_Bench\n",
"from utils.tsp import TSP_Bench_ALL"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Workshop Starts Here"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"<img src=\"images/tsp.jpg\" alt=\"TSP\" style=\"width: 900px;\"/>"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"<img src=\"images/solutions.png\" alt=\"solutions\" style=\"width: 900px;\"/>"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Get familiar with your dataset"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"There are problems at different levels. **3 simple, 2 medium, 1 hard**."
]
},
{
"cell_type": "code",
"execution_count": 3,
"metadata": {
"scrolled": false
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"./template/data/medium/pcb442.tsp\n",
"./template/data/medium/a280.tsp\n",
"./template/data/hard/dsj1000.tsp\n",
"./template/data/simple/att48.tsp\n",
"./template/data/simple/ulysses16.tsp\n",
"./template/data/simple/st70.tsp\n"
]
}
],
"source": [
"for root, _, files in os.walk('./template/data'):\n",
" if(files):\n",
" for f in files:\n",
" print(str(root) + \"/\" + f)"
]
},
{
"cell_type": "code",
"execution_count": 4,
"metadata": {},
"outputs": [],
"source": [
"ulysses16 = np.array(load_data(\"./template/data/simple/ulysses16.tsp\"))"
]
},
{
"cell_type": "code",
"execution_count": 5,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"array([[38.24, 20.42],\n",
" [39.57, 26.15],\n",
" [40.56, 25.32],\n",
" [36.26, 23.12],\n",
" [33.48, 10.54],\n",
" [37.56, 12.19],\n",
" [38.42, 13.11],\n",
" [37.52, 20.44],\n",
" [41.23, 9.1 ],\n",
" [41.17, 13.05],\n",
" [36.08, -5.21],\n",
" [38.47, 15.13],\n",
" [38.15, 15.35],\n",
" [37.51, 15.17],\n",
" [35.49, 14.32],\n",
" [39.36, 19.56]])"
]
},
"execution_count": 5,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"ulysses16[:]"
]
},
{
"cell_type": "code",
"execution_count": 6,
"metadata": {
"scrolled": true
},
"outputs": [
{
"data": {
"image/png": "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\n",
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plt.scatter(ulysses16[:, 0], ulysses16[:, 1])\n",
"for i in range(0, 16):\n",
" plt.annotate(i, (ulysses16[i, 0], ulysses16[i, 1]+0.5))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Naive Solution: In Order"
]
},
{
"cell_type": "code",
"execution_count": 7,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]\n"
]
}
],
"source": [
"simple_sequence = list(range(0, 16))\n",
"print(simple_sequence)"
]
},
{
"cell_type": "code",
"execution_count": 8,
"metadata": {},
"outputs": [
{
"data": {
"image/png": "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\n",
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plotTSP([simple_sequence], ulysses16, num_iters=1)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Naive Solution: Random Permutation"
]
},
{
"cell_type": "code",
"execution_count": 9,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"[6, 1, 13, 11, 15, 14, 9, 8, 0, 12, 7, 5, 4, 3, 10, 2]\n"
]
}
],
"source": [
"random_permutation = np.random.permutation(16).tolist()\n",
"print(random_permutation)"
]
},
{
"cell_type": "code",
"execution_count": 10,
"metadata": {},
"outputs": [
{
"data": {
"image/png": "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\n",
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plotTSP([random_permutation], ulysses16, num_iters=1)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Best Solution"
]
},
{
"cell_type": "code",
"execution_count": 11,
"metadata": {},
"outputs": [
{
"data": {
"image/png": "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\n",
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"best_ulysses16 = [0, 13, 12, 11, 6, 5, 14, 4, 10, 8, 9, 15, 2, 1, 3, 7]\n",
"plotTSP([best_ulysses16], ulysses16, num_iters=1)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Calculate Fitness (Sum of all Distances)"
]
},
{
"cell_type": "code",
"execution_count": 12,
"metadata": {},
"outputs": [],
"source": [
"def dist(node_0, node_1, coords):\n",
" \"\"\"\n",
" Euclidean distance between two nodes.\n",
" \"\"\"\n",
" coord_0, coord_1 = coords[node_0], coords[node_1]\n",
" return math.sqrt((coord_0[0] - coord_1[0]) ** 2 + (coord_0[1] - coord_1[1]) ** 2)"
]
},
{
"cell_type": "code",
"execution_count": 13,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Coordinate of City 0: [38.24 20.42]\n"
]
}
],
"source": [
"print(\"Coordinate of City 0:\", ulysses16[0])"
]
},
{
"cell_type": "code",
"execution_count": 14,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Coordinate of City 1: [39.57 26.15]\n"
]
}
],
"source": [
"print(\"Coordinate of City 1:\", ulysses16[1])"
]
},
{
"cell_type": "code",
"execution_count": 15,
"metadata": {
"scrolled": true
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Distance Between 5.882329470541408\n"
]
}
],
"source": [
"print(\"Distance Between\", dist(0, 1, ulysses16))"
]
},
{
"cell_type": "code",
"execution_count": 16,
"metadata": {},
"outputs": [],
"source": [
"def fitness(solution, coords):\n",
" N = len(coords)\n",
" cur_fit = 0\n",
" for i in range(len(solution)):\n",
" cur_fit += dist(solution[i % N], solution[(i + 1) % N], coords)\n",
" return cur_fit"
]
},
{
"cell_type": "code",
"execution_count": 17,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Order Fitness:\t 104.42225210207233\n",
"Random Fitness:\t 165.05253084971622\n",
"Best Fitness:\t 74.10873595815309\n"
]
}
],
"source": [
"print (\"Order Fitness:\\t\", fitness(simple_sequence, ulysses16))\n",
"print (\"Random Fitness:\\t\", fitness(random_permutation, ulysses16))\n",
"print (\"Best Fitness:\\t\", fitness(best_ulysses16, ulysses16))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Naive Random Model"
]
},
{
"cell_type": "code",
"execution_count": 18,
"metadata": {},
"outputs": [],
"source": [
"import math\n",
"import random\n",
"from model.base_model import Model\n",
"\n",
"class MyRandomModel(Model):\n",
" def __init__(self):\n",
" super().__init__()\n",
"\n",
" def init(self, nodes):\n",
" \"\"\"\n",
" Put your initialization here.\n",
" \"\"\"\n",
" super().init(nodes)\n",
"\n",
" def fit(self, max_it):\n",
" \"\"\"\n",
" Put your iteration process here.\n",
" \"\"\"\n",
" random_solutions = []\n",
" for i in range(0, max_it):\n",
" solution = np.random.permutation(self.N).tolist()\n",
" random_solutions.append(solution)\n",
" self.fitness_list.append(self.fitness(solution))\n",
"\n",
" self.best_solution = random_solutions[self.fitness_list.index(min(self.fitness_list))]\n",
" return self.best_solution, self.fitness_list"
]
},
{
"cell_type": "code",
"execution_count": 19,
"metadata": {},
"outputs": [],
"source": [
"tsp_file = './template/data/simple/ulysses16.tsp'"
]
},
{
"cell_type": "code",
"execution_count": 20,
"metadata": {
"scrolled": true
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"[*] [Node] 16, [Best] 102.73430244116014\n",
"[*] Running for: 0.01 seconds\n",
"\n"
]
}
],
"source": [
"model = MyRandomModel()\n",
"best_solution, fitness_list, time = TSP_Bench(tsp_file, model, max_it=100)"
]
},
{
"cell_type": "code",
"execution_count": 21,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"[<matplotlib.lines.Line2D at 0x7f935af45d00>]"
]
},
"execution_count": 21,
"metadata": {},
"output_type": "execute_result"
},
{
"data": {
"image/png": "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\n",
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plt.plot(fitness_list, 'o-')"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Simulated Annealing"
]
},
{
"cell_type": "code",
"execution_count": 22,
"metadata": {},
"outputs": [],
"source": [
"import math\n",
"import random\n",
"from model.base_model import Model\n",
"\n",
"class MySAModel(Model):\n",
" def __init__(self):\n",
" super().__init__()\n",
"\n",
" self.iteration = 0\n",
"\n",
" def init(self, nodes, *args):\n",
" super().init(nodes)\n",
"\n",
" T, stopping_temperature, alpha = args\n",
"\n",
" self.T = math.sqrt(self.N) if T == -1 else T\n",
" self.alpha = 0.995 if alpha == -1 else alpha\n",
" self.stopping_temperature = 1e-8 if stopping_temperature == -1 else stopping_temperature\n",
"\n",
" self.T_save = self.T # save inital T to reset if batch annealing is used\n",
"\n",
" def initial_solution(self):\n",
" \"\"\"\n",
" Greedy algorithm to get an initial solution (closest-neighbour).\n",
" \"\"\"\n",
" cur_node = random.choice(self.nodes) # start from a random node\n",
" solution = [cur_node]\n",
"\n",
" free_nodes = set(self.nodes)\n",
" free_nodes.remove(cur_node)\n",
" while free_nodes:\n",
" next_node = min(free_nodes, key=lambda x: self.dist(cur_node, x)) # nearest neighbour\n",
" free_nodes.remove(next_node)\n",
" solution.append(next_node)\n",
" cur_node = next_node\n",
"\n",
" cur_fit = self.fitness(solution)\n",
" if cur_fit < self.best_fitness: # If best found so far, update best fitness\n",
" self.best_fitness = cur_fit\n",
" self.best_solution = solution\n",
" self.fitness_list.append(cur_fit)\n",
" return solution, cur_fit\n",
"\n",
" def p_accept(self, candidate_fitness):\n",
" \"\"\"\n",
" Probability of accepting if the candidate is worse than current.\n",
" Depends on the current temperature and difference between candidate and current.\n",
" \"\"\"\n",
" return math.exp(-abs(candidate_fitness - self.cur_fitness) / self.T)\n",
"\n",
" def accept(self, candidate):\n",
" \"\"\"\n",
" Accept with probability 1 if candidate is better than current.\n",
" Accept with probabilty p_accept(..) if candidate is worse.\n",
" \"\"\"\n",
" candidate_fitness = self.fitness(candidate)\n",
" if candidate_fitness < self.cur_fitness:\n",
" self.cur_fitness, self.cur_solution = candidate_fitness, candidate\n",
" if candidate_fitness < self.best_fitness:\n",
" self.best_fitness, self.best_solution = candidate_fitness, candidate\n",
" else:\n",
" if random.random() < self.p_accept(candidate_fitness):\n",
" self.cur_fitness, self.cur_solution = candidate_fitness, candidate\n",
"\n",
" def fit(self, max_it):\n",
" \"\"\"\n",
" Execute simulated annealing algorithm.\n",
" \"\"\"\n",
" # Initialize with the greedy solution.\n",
" self.cur_solution, self.cur_fitness = self.initial_solution()\n",
"\n",
" self.log(\"Starting annealing.\")\n",
" while self.T >= self.stopping_temperature and self.iteration < max_it:\n",
" candidate = list(self.cur_solution)\n",
" l = random.randint(1, self.N - 1)\n",
" i = random.randint(0, self.N - l)\n",
" candidate[i : (i + l)] = reversed(candidate[i : (i + l)])\n",
" self.accept(candidate)\n",
" self.T *= self.alpha\n",
" self.iteration += 1\n",
"\n",
" self.fitness_list.append(self.cur_fitness)\n",
"\n",
" self.log(f\"Best fitness obtained: {self.best_fitness}\")\n",
" improvement = 100 * (self.fitness_list[0] - self.best_fitness) / (self.fitness_list[0])\n",
" self.log(f\"Improvement over greedy heuristic: {improvement : .2f}%\")\n",
"\n",
" return self.best_solution, self.fitness_list"
]
},
{
"cell_type": "code",
"execution_count": 23,
"metadata": {},
"outputs": [],
"source": [
"tsp_file = './template/data/simple/ulysses16.tsp'"
]
},
{
"cell_type": "code",
"execution_count": 24,
"metadata": {},
"outputs": [],
"source": [
"# Set hyper-parameters\n",
"T = -1\n",
"stopping_T = -1\n",
"alpha = 0.99"
]
},
{
"cell_type": "code",
"execution_count": 25,
"metadata": {
"scrolled": true
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"[MySAModel] Starting annealing.\n",
"[MySAModel] Best fitness obtained: 74.19894280657067\n",
"[MySAModel] Improvement over greedy heuristic: 28.71%\n",
"[*] [Node] 16, [Best] 74.19894280657067\n",
"[*] Running for: 0.02 seconds\n",
"\n"
]
}
],
"source": [
"model = MySAModel()\n",
"best_solution, fitness_list, time = TSP_Bench(tsp_file, model, T, stopping_T, alpha, max_it=1000)"
]
},
{
"cell_type": "code",
"execution_count": 26,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"[<matplotlib.lines.Line2D at 0x7f935af30e50>]"
]
},
"execution_count": 26,
"metadata": {},
"output_type": "execute_result"
},
{
"data": {
"image/png": "iVBORw0KGgoAAAANSUhEUgAAAXcAAAD4CAYAAAAXUaZHAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjMuMywgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/Il7ecAAAACXBIWXMAAAsTAAALEwEAmpwYAAAbn0lEQVR4nO3df3Rc5X3n8fdXI2Fkdze2sPDawsTEdZySONipAvY6SQkkMSVpUQkJeCFlCcU9PeSEH622dktjktLF1GxIm/aQQkPDLpTwI44gJEEQIE3Xi90VkUHmh2IcgrFssAiYdEEHpNF3/7h35LE8I41m7sxonvm8ztGZmedezTzX1+ejZ5773Ocxd0dERMLSUO0KiIhI8hTuIiIBUriLiARI4S4iEiCFu4hIgBqrXQGAuXPn+qJFi6pdDRGRmvL444+/4u6tubZNi3BftGgRPT091a6GiEhNMbMX8m1Tt4yISIAU7iIiAVK4i4gESOEuIhIghbuISICmxWiZJHT1DrC5u599B4dYMLuZzjVL6VjRVu1qiYhURRDh3tU7wIYtfQwNpwEYODjEhi19AAp4EalLQXTLbO7uHwv2jKHhNJu7+6tUIxGR6goi3PcdHJpSuYhI6III9wWzm6dULiISuiDCvXPNUo5uOvxQmptSdK5ZWqUaiYhUVxAXVDtWtDGSHuVP7nkSgDaNlhGROhdEyx3gzPfPH3u+df1pCnYRqWvBhHt6VAt9i4hkBBPuo6PRo1l16yEiMh0EE+5pj1ruynYRkZDCPe6WaVDTXURE4S4iEqJwwj3ullG/jIhIAeFuZreY2QEz25lV1mJmD5nZrvhxTlx+qpm9bmY74p8vlbPy2UbHWu6V+kQRkemrkJb7t4AzxpWtBx529yXAw/HrjH919+Xxz1eSqebkMt0ypqa7iMjk4e7uPwFeHVd8FnBr/PxWoCPZak3d2GgZZbuISNF97vPcfX/8/CVgXta2VWb2hJn90Mzem+8NzGydmfWYWc/g4GCR1ThkVBdURUTGlHxB1d0dyNwe+lPgne5+EvB1oGuC37vJ3dvdvb21tbXUajAyqpa7iEhGseH+spnNB4gfDwC4+6/c/f/Fz38ANJnZ3ERqOolDfe4iIlLsrJD3ARcCm+LHewHM7D8BL7u7m9nJRH88fplERccbv2bquR88jrgO5fg4EZGaMmm4m9kdwKnAXDPbC2wkCvW7zOxi4AXgs/Hu5wB/ZGYjwBBwXtxtk6hca6b+/aO7AQ2FFBGBAsLd3dfm2XR6jn3/Dvi7Uis1mVxrpr41Es0cpguqIiI1eofqRGujKttFRGo03CdaG1V97iIiNRrunWuW0tyUyrlt8N/f4vybH6twjUREppeaDPeOFW0cN+fovNu37n5VAS8ida0mwx1g14E3Jty+dff4GRNEROpHzYa7iIjkp3AXEQlQzYb76sUtJW0XEQlZzYb77Zesyhvgqxe3cPslqypcIxGR6aNmwx2igP/Fpk/ykXcfmlXyo0tbFewiUvdqOtwhmmdm665D88H/665X6OodqGKNRESqr6bDvat3gM67nyCdNTXZyKjTec8TCngRqWs1He6bu/sZHj1y0snhtLO5u78KNRIRmR5qOtwnmkBsom0iIqGr6XCfaAKxibaJiISupsO9c81SmnKsztGUMjrXLK1CjUREpoeaDveOFW1s/sxJzG5uGitrbDA2n3MSHSvaqlgzEZHqKnYN1WmjY0XbWJD/l5u3MZweVbCLSN2r6Zb7eGaQY/CMiEjdCSrcG8wow3rcIiI1J6hwNzO13EVEKCDczewWMztgZjuzylrM7CEz2xU/zonLzcz+1syeM7MnzewD5az8EXUFtdxFRCis5f4t4IxxZeuBh919CfBw/Brgt4El8c864MZkqlmYBgNFu4hIAeHu7j8Bxq9ZdxZwa/z8VqAjq/x/emQbMNvM5idU10k1mDGqlruISNF97vPcfX/8/CVgXvy8DXgxa7+9cdkRzGydmfWYWc/g4GCuXabMDEZHE3krEZGaVvIFVY86uafcXHb3m9y93d3bW1tbJ/+FApha7iIiQPHh/nKmuyV+PBCXDwALs/Y7Li6riBwzEYiI1KViw/0+4ML4+YXAvVnlvx+PmlkJvJ7VfVN26nMXEYlMOv2Amd0BnArMNbO9wEZgE3CXmV0MvAB8Nt79B8CZwHPAm8BFZajzBHXVHaoiIlBAuLv72jybTs+xrwOXllqpYpnuUBURAQK7QzWafqDatRARqb5gwr2rd4AfPf0yP3/lDVZvekRrqIpIXQsi3Lt6B9iwpY+h4TQAAweH2LClTwEvInUriHDf3N0/FuwZQ8NpLZItInUriHDPtxi2FskWkXoVRLjnWwxbi2SLSL0KItw71yyluSl1WFlzU0qLZItI3ar5NVSBsTVT/+y7fbz5dpq22c10rlmqtVRFpG4FEe4QBfz253/Jj545wNb1p1W7OiIiVRVEt0yG6SYmEREgsHBvMC2zJyICgYW7oVkhRUQgsHDXGqoiIpGgwt3MGNWcvyIioYU7uqAqIkJg4d5gpm4ZERGCC3d0QVVEhODCXaNlREQgsHBHa6iKiACBhXuDaSykiAgEF+7qcxcRgRLD3cwuM7OdZvaUmV0el11tZgNmtiP+OTORmhZSH92hKiIClDArpJm9D7gEOBl4G3jAzO6PN9/g7tcnUL8p0R2qIiKRUqb8/Q1gu7u/CWBm/wKcnUitipSZFdLdMbNqVkVEpKpK6ZbZCXzYzI4xs5nAmcDCeNsXzOxJM7vFzObk+mUzW2dmPWbWMzg4WEI1st8zelTPjIjUu6LD3d2fAa4DHgQeAHYAaeBGYDGwHNgP/I88v3+Tu7e7e3tra2ux1ThMQ5zuynYRqXclXVB192+6+2+6+0eA14CfufvL7p5291HgZqI++YpoiFvuuqgqIvWu1NEyx8aPxxP1t/+zmc3P2uX3iLpvKiLTz65wF5F6V+oaqt8xs2OAYeBSdz9oZl83s+VEvSO/AP6wxM8omPrcRUQiJYW7u384R9nnSnnPUoz1uSvcRaTOBXeHKqhbRkQkqHA31OcuIgKhhXumz7261RARqbqgwn2sz320yhUREamyoMLd1OcuIgIEFu66Q1VEJBJYuEeParmLSL0LKtx1h6qISCSwcI8ele0iUu9KnX5g2ujqHeAvvhtNY3PKf38YgBmNDVz36ffTsaKtmlUTEam4IMK9q3eAy+/ccUT5WyOjXHlXVK6AF5F6EkS3zObu/rzbRn3i7SIiIQqi5b7v4NCk26/q6uOO7S+SdidlxtpTFnJNx7IK1VBEpLKCaLkvmN084fajmxq4bdse0vGV1rQ7t23bw1VdfZWonohIxQUR7p1rlubd1mBR33sud2x/sVxVEhGpqiDCvWNFG187dzlN445mRmMDX/3sckbzDI1Ma8ykiAQqiD53iAK+Y0Ubr785zElfeZAvfepEPv+hEwD447ueyBnkqczAeBGRwATRcs+WSkWBPTJ6qCtm7SkLc+6br1xEpNYFF+6N8QQzw+lDLfVrOpbRsXzB2OuUGResPF6jZUQkWMF0y2Q0paK/V+lxHe2XfezddO3YB8Dua8+seL1ERCopuJZ7ZmbIkfThI2TSo1rBQ0TqR0nhbmaXmdlOM3vKzC6Py1rM7CEz2xU/zkmkpoXXiaaUMTyu5T6Sb8iMiEiAiu6WMbP3AZcAJwNvAw+Y2f3AOuBhd99kZuuB9cCfJlHZQjU2NPDs/l+xetMj7Ds4xILZzZx3si6eikj9KKXP/TeA7e7+JoCZ/QtwNnAWcGq8z63Aj6lwuI/6KD/Z9cpYv/vAwSG+9tDPxrYvWv99AFYvbuH2S1ZVsmoiIhVRSrfMTuDDZnaMmc0EzgQWAvPcfX+8z0vAvFy/bGbrzKzHzHoGBwdLqMaRhtN+xAXVdI5ema27X+X8mx9L9LNFRKaDosPd3Z8BrgMeBB4AdgDpcfs4eZY0dfeb3L3d3dtbW1uLrcYRrurqy3tHai5bd7+a2GeLiEwXJV1QdfdvuvtvuvtHgNeAnwEvm9l8gPjxQOnVLMxVXX3ctm1PpT5ORGTaKnW0zLHx4/FE/e3/DNwHXBjvciFwbymfMRWaCExEJFLqTUzfMbNjgGHgUnc/aGabgLvM7GLgBeCzpVayUMVMBLZ6cUsZaiIiUl0lhbu7fzhH2S+B00t532KlzKYU8BotIyKhCmr6gbWnLCy4z33nl9fwazOCOnwRkTFBTT9wTccyLlh5fEH7fvm+p8pcGxGR6gkq3CEK+ELmab/78b0VqI2ISHUEF+6gFZZERIIMd62wJCL1LshwL3SFpdWbHqGrd6DMtRERqbwgw/2ajmUU0nYfODjEhi19CngRCU6Q4Q5wfoGjZoaG02zu7i9zbUREKivYcJ/KsMh9B4fKXBsRkcoK+i6eazqWHbYI9upNjzCQI8gXzG6uZLVERMou2JZ7Lp1rljKj8fBDbm5K0blmaZVqJCJSHnUV7h0r2vji6UvGXrfNbubas5fRsaKtirUSEUle0N0yuax57zw2d/fz9bUr+J2TFlS7OiIiZVFXLXeAplR0yMPp0SrXRESkfOou3I+K+9zfHlG4i0i46i7c1XIXkXpQt+H+dlqTi4lIuOou3I9Sy11E6kDdhfsP+/YBsOmHz2riMBEJVl2Fe1fvAH/edWgFJk0cJiKhKmmcu5ldAfwB4EAfcBHwDeC3gNfj3f6ru+8o5XOSsrm7n6Hh9GFl2ROHXXnnDibrrFm9uIUD//4Wuw68kXP7jMYGrvv0+3VjlIhUVdHhbmZtwBeBE919yMzuAs6LN3e6+z1JVDBJ+SYIGzg4xOV37ijoPbbufnXC7W+NjHLlXdF7KeBFpFpK7ZZpBJrNrBGYCewrvUrlk2+CsKRXbhp1NI2wiFRV0eHu7gPA9cAeYD/wurs/GG/+KzN70sxuMLMZCdQzEYuOyR3u5VhzVdMIi0g1FR3uZjYHOAs4AVgAzDKzC4ANwHuADwItwJ/m+f11ZtZjZj2Dg4PFVmNKtv38tYp8DsDRTXV1rVpEpplSEuhjwPPuPujuw8AW4D+7+36PvAX8E3Byrl9295vcvd3d21tbW0uoRuHK0ULPZ2h4lKu6+ir2eSIi2UoJ9z3ASjObaWYGnA48Y2bzAeKyDmBnybVMSBJ966sXt7DgHYX1NN2x/cWSP09EpBil9LlvB+4Bfko0DLIBuAm43cz64rK5wDUJ1DMRa09ZOKX9U2b8YtMn2XR2tJrT/1l/GrdfsoqvnBW9/t4XPjTh71fym4KISLaSxrm7+0Zg47ji00p5z3K6pmMZt23bU/D+mXBujKcsSI9GrzNTFzQ1TvxNIOlROCIihaq7xTqmIhPOjQ3R40gc7m9nwj3VwOrFLXnHvo//ptDVO0Dn3TsYznGn1AUrjz9svVcRkVLUXbhPFMbjZcI5FYd7ejRK5eF4RsmjUg3cfskqzr/5sZzvedu2PQV/U8jsp4AXkSTU3Xi92y9ZxerFLZPul92SPqLlPnKo5Q7wmfbjE6mbLsCKSFLqruUOUcBPRablPpIe1+eeisqTuhtVF2BFJCl113IvRmPqUMv9qq4+rv5eNLPkB//qR1zV1Zfo3ajn3/xYYu8lIvWrLlvuU5VqiP4G3vjoLrqfPjBWPupRX/mso1K88XY6369PSaHXA0REJqKWewGa4m6Zh545kHP7mwkFu4hIUhTuBcj0uY/m6RJ34GvnLkfTyYjIdKFumQJk+twbLHfAp8zoWNF22PztXb0DBc8Rn62QkTwiIpNRW7MAmT7333r33Jzbc01rUMwImtWLW6Y8kkdEJBe13Auw8d5odsdH+185rDxlxtpTFua88WgqI2j+w9GN9F29prRKiohkUct9Euff/BhP7P1Vzm3vap2Z947SfKs+HbHff5wxNmeNiEhSFO6TmGhoYr5FsgE61yyluSk14XuvXtzC7644buzOVxGRpKhbpkwyF1c3d/ez7+AQC2Y307lm6RGLZl/f3a+Wu4gkTuFeRuNH0OSSajDSo467Y5oiWEQSom6ZSUw0NHHJsbNKfv/GsRkn1XoXkeQo3CeRbxbJdxyd4qErTy35/VOpw2ecFBFJgrplCpAZe/6/d73CBd/cDsB5J78zkfdWy11EykEt9yloyPrXykxJUKrMDVJquYtIkhTuU9CYle6NCYW7Wu4iUg4K9ynIbq03JNZyz/S551hYVUSkSCX1uZvZFcAfEE2M2AdcBMwHvg0cAzwOfM7d3y6xntNCdrgn1XJPTdJy7+od4Mo7d5Ad/UuOnZXIxVwRCVfR4W5mbcAXgRPdfcjM7gLOA84EbnD3b5vZN4CLgRsTqW2VZQd6qiGZLz1P7D0IwKprHzmsfMmxs7j0o0tyziy568AbfPyrP1bAi0hepSZUI9BsZo3ATGA/cBpwT7z9VqCjxM+YNhosO9xLf7+ruvr49r/lXhR714E3+JO7n8j7uxNNfSAiUnREufsAcD2whyjUXyfqhjno7iPxbnuBnLdomtk6M+sxs57BwcFiq1FRmXndofSWe1fvALdt2zPhPhpBIyLFKjqhzGwOcBZwArAAmAWcUejvu/tN7t7u7u2tra3FVqOiHu0/tMzeX97/NCu+8iBdvQNFvVcx872LiBSqlObnx4Dn3X3Q3YeBLcBqYHbcTQNwHFBc+k0zXb0D/PUPnz2s7LU3h+m854miAn4q873nksTUByISrlJGy+wBVprZTGAIOB3oAR4FziEaMXMhcG+plZwONnf3k87RSzKcdjZ39086Qdh4C2Y3MzBJwOe7qJprtExX7wCdd+9geNyISq3uJFKfzL34fl0z+zJwLjAC9BINi2wjCvaWuOwCd39rovdpb2/3np6eoutRCYvWfz/vNgOe3/TJKb1friGO5aKAFwmTmT3u7u25tpU0zt3dNwIbxxX/HDi5lPedjlJmpPP8ISx01aVsmZb+hi1PMjS+uZ2wiRYcEZEwaeKwAuULdohWXSpG9nzvE30zEBGZKk0/UKC2PK3z2c1NU+5vFxEpN4V7gT76ntzDNT910vwK16Q459/8WLWrICIVpHAv0KPP5r7RKl/5VE204lMStu5+VQEvUkcU7gXKNy691PHqGflWfEqSLqyK1A9dUC1QvnHpxYyUySczXLGrd4Cr73uKg0PDAMyZ2cTG33nvpH37J6z/PpqwQERA4V6wzjVL2bClj6Hh9FhZc1Oq6JEyE8keRTMVhdwYJSL1Qd0yBepY0ca1Zy+jbXYzRjR65tqzl02rkTKT/aEpd7ePiEwfarlPQbEt6krJ1E3TEIiIwj0w2X+AvrX1ea7+3tP89C8+Tsuso6pcMxGpJHXLBKwxXlFkJK31WUXqjcI9YE3x4iLDWvRDpO4o3APW2KCWu0i9UrgHLLMsoJbrE6k/CveAHWq5K9xF6o3CPWCZlvuwumVE6o7CPWBN6pYRqVsK94DpgqpI/dJNTAHbsOUJAM75Ru6pfhsbjOs/c9K0vutWRIqjlnugPv7VHzNwcMJ1yRkZda64cwddvQMVqpWIVIrCPVC7DrxR0H4ObO7uL29lRKTiiu6WMbOlwJ1ZRe8CvgTMBi4BMksU/Zm7/6DYz5HyS2rBERGZPooOd3fvB5YDmFkKGAC+C1wE3ODu1ydRQSm/JBccEZHpIalumdOB3e7+QkLvJyVacuysgvYzJp8HXkRqT1Lhfh5wR9brL5jZk2Z2i5nNyfULZrbOzHrMrGdwMJlFpuWQh648ddKAb2wwbjh3uUbLiATI3Eu7wcXMjgL2Ae9195fNbB7wCtG1ur8E5rv75yd6j/b2du/p6SmpHlKYq7r6uG3bnqp9/ozGBq779Pv1B0UkAWb2uLu359yWQLifBVzq7p/IsW0RcL+7v2+i91C4V0a1g11Eciv2npOJwj2Jbpm1ZHXJmNn8rG2/B+xM4DMkAXdsf7HaVRCRHMpxz0lJ4W5ms4CPA1uyiv/azPrM7Engo8AVpXyGJCdd4rc0ESmfpO85KWn6AXd/AzhmXNnnSqqRlE3KTAEvMo0lec+J7lCtI2tPWVjtKojIBJK850ThXkeu6VjGBSuPr3Y1RCSHpO85KXm0TBI0WiZsGqUjMrFyjJZRuIuI1KhyD4UUEZFpRuEuIhIghbuISIAU7iIiAVK4i4gEaFqMljGzQaDYueDnEs1CWU90zPVBx1wfSjnmd7p7a64N0yLcS2FmPfmGAoVKx1wfdMz1oVzHrG4ZEZEAKdxFRAIUQrjfVO0KVIGOuT7omOtDWY655vvcRUTkSCG03EVEZByFu4hIgGo63M3sDDPrN7PnzGx9teuTFDNbaGaPmtnTZvaUmV0Wl7eY2UNmtit+nBOXm5n9bfzv8KSZfaC6R1AcM0uZWa+Z3R+/PsHMtsfHdaeZHRWXz4hfPxdvX1TVihfJzGab2T1m9qyZPWNmq+rgHF8R/5/eaWZ3mNnRoZ1nM7vFzA6Y2c6ssimfVzO7MN5/l5ldONV61Gy4m1kK+Hvgt4ETgbVmdmJ1a5WYEeCP3f1EYCVwaXxs64GH3X0J8HD8GqJ/gyXxzzrgxspXORGXAc9kvb4OuMHdfx14Dbg4Lr8YeC0uvyHerxb9DfCAu78HOIno2IM9x2bWBnwRaHf39wEp4DzCO8/fAs4YVzal82pmLcBG4BTgZGBj5g9Cwdy9Jn+AVUB31usNwIZq16tMx3ov0ULk/cD8uGw+0B8//wdgbdb+Y/vVyg9wXPyf/jTgfqKFaV4BGsefb6AbWBU/b4z3s2ofwxSP9x3A8+PrHfg5bgNeBFri83Y/sCbE8wwsAnYWe16BtcA/ZJUftl8hPzXbcufQf5SMvXFZUOKvoiuA7cA8d98fb3oJmBc/D+Hf4mvAfwNG49fHAAfdfSR+nX1MY8cbb3+dcQu114ATgEHgn+KuqH80s1kEfI7dfQC4HtgD7Cc6b48T9nnOmOp5Lfl813K4B8/Mfg34DnC5u/8qe5tHf86DGMdqZp8CDrj749WuSwU1Ah8AbnT3FcAbHPqqDoR1jgHiboWziP6wLQBmcWT3RfAqdV5rOdwHgIVZr4+Ly4JgZk1EwX67u2+Ji182s/nx9vnAgbi81v8tVgO/a2a/AL5N1DXzN8BsM2uM98k+prHjjbe/A/hlJSucgL3AXnffHr++hyjsQz3HAB8Dnnf3QXcfBrYQnfuQz3PGVM9ryee7lsP9/wJL4ivtRxFdmLmvynVKhJkZ8E3gGXf/atam+4DMVfMLifriM+W/H195Xwm8nvUVcNpz9w3ufpy7LyI6j4+4+/nAo8A58W7jjzfz73BOvH9NtXDd/SXgRTPLLHd/OvA0gZ7j2B5gpZnNjP+PZ4452POcZarntRv4hJnNib/xfCIuK1y1LzyUeNHiTOBnwG7gz6tdnwSP60NEX9ueBHbEP2cS9Tc+DOwCfgS0xPsb0cih3UAf0WiEqh9Hkcd+KnB//PxdwL8BzwF3AzPi8qPj18/F299V7XoXeazLgZ74PHcBc0I/x8CXgWeBncD/AmaEdp6BO4iuKQwTfUO7uJjzCnw+PvbngIumWg9NPyAiEqBa7pYREZE8FO4iIgFSuIuIBEjhLiISIIW7iEiAFO4iIgFSuIuIBOj/A5+rABvwnaBIAAAAAElFTkSuQmCC\n",
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plt.plot(fitness_list, 'o-')"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Your Smart Model"
]
},
{
"cell_type": "code",
"execution_count": 27,
"metadata": {},
"outputs": [],
"source": [
"import math\n",
"import random\n",
"from model.base_model import Model\n",
"\n",
"class MyModel(Model):\n",
" def __init__(self):\n",
" super().__init__()\n",
"\n",
" def init(self, nodes):\n",
" \"\"\"\n",
" Put your initialization here.\n",
" \"\"\"\n",
" super().init(nodes)\n",
" self.log(\"Nothing to initialize in your model now\")\n",
"\n",
" def fit(self, max_it):\n",
" \"\"\"\n",
" Put your iteration process here.\n",
" \"\"\"\n",
" self.log(\"Naive Random Solution\")\n",
" self.best_solution = np.random.permutation(self.N).tolist()\n",
" self.fitness_list.append(self.fitness(self.best_solution))\n",
"\n",
" return self.best_solution, self.fitness_list"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Test your Model"
]
},
{
"cell_type": "code",
"execution_count": 28,
"metadata": {},
"outputs": [],
"source": [
"tsp_file = './template/data/simple/ulysses16.tsp'"
]
},
{
"cell_type": "code",
"execution_count": 29,
"metadata": {
"scrolled": true
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"[MyModel] Nothing to initialize in your model now\n",
"[MyModel] Naive Random Solution\n",
"[*] [Node] 16, [Best] 154.5735310725095\n",
"[*] Running for: 0.00 seconds\n",
"\n"
]
}
],
"source": [
"model = MyModel()\n",
"best_solution, fitness_list, time = TSP_Bench(tsp_file, model)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Test All Dataset"
]
},
{
"cell_type": "code",
"execution_count": 30,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"./template/data/medium/pcb442.tsp\n",
"./template/data/medium/a280.tsp\n",
"./template/data/hard/dsj1000.tsp\n",
"./template/data/simple/att48.tsp\n",
"./template/data/simple/ulysses16.tsp\n",
"./template/data/simple/st70.tsp\n"
]
}
],
"source": [
"for root, _, files in os.walk('./template/data'):\n",
" if(files):\n",
" for f in files:\n",
" print(str(root) + \"/\" + f)"
]
},
{
"cell_type": "code",
"execution_count": 31,
"metadata": {},
"outputs": [],
"source": [
"def plot_results(best_solutions, times, title):\n",
" fig = plt.figure()\n",
" nodes = [len(s) for s in best_solutions]\n",
" data = np.array([[node, time] for node, time in sorted(zip(nodes, times))])\n",
" plt.plot(data[:, 0], data[:, 1], 'o-')\n",
" fig.suptitle(title, fontsize=20)"
]
},
{
"cell_type": "code",
"execution_count": 32,
"metadata": {},
"outputs": [],
"source": [
"tsp_path = './template/data'"
]
},
{
"cell_type": "code",
"execution_count": 33,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Random Search\n",
"[*] ./template/data/medium/pcb442.tsp\n",
"[*] [Node] 442, [Best] 721524.9399929157\n",
"[*] Running for: 0.42 seconds\n",
"\n",
"[*] ./template/data/medium/a280.tsp\n",
"[*] [Node] 280, [Best] 31159.560032157442\n",
"[*] Running for: 0.26 seconds\n",
"\n",
"[*] ./template/data/hard/dsj1000.tsp\n",
"[*] [Node] 1000, [Best] 524396404.5171182\n",
"[*] Running for: 0.87 seconds\n",
"\n",
"[*] ./template/data/simple/att48.tsp\n",
"[*] [Node] 48, [Best] 123105.46532911454\n",
"[*] Running for: 0.05 seconds\n",
"\n",
"[*] ./template/data/simple/ulysses16.tsp\n",
"[*] [Node] 16, [Best] 103.01947175501947\n",
"[*] Running for: 0.02 seconds\n",
"\n",
"[*] ./template/data/simple/st70.tsp\n",
"[*] [Node] 70, [Best] 3084.3745918065306\n",
"[*] Running for: 0.05 seconds\n",
"\n"
]
}
],
"source": [
"model = MyRandomModel()\n",
"\n",
"print(\"Random Search\")\n",
"best_solutions, fitness_lists, times = TSP_Bench_ALL(tsp_path, model)"
]
},
{
"cell_type": "code",
"execution_count": 34,
"metadata": {},
"outputs": [
{
"data": {
"image/png": "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\n",
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plot_results(best_solutions, times, \"Random Model\")"
]
},
{
"cell_type": "code",
"execution_count": 35,
"metadata": {},
"outputs": [],
"source": [
"# Set hyper-parameters\n",
"T = -1\n",
"stopping_T = -1\n",
"alpha = 0.8"
]
},
{
"cell_type": "code",
"execution_count": 36,
"metadata": {
"scrolled": true
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Simulated Annealing\n",
"[*] ./template/data/medium/pcb442.tsp\n",
"[MySAModel] Starting annealing.\n",
"[MySAModel] Best fitness obtained: 62562.051863573186\n",
"[MySAModel] Improvement over greedy heuristic: 0.02%\n",
"[*] [Node] 442, [Best] 62562.051863573186\n",
"[*] Running for: 0.09 seconds\n",
"\n",
"[*] ./template/data/medium/a280.tsp\n",
"[MySAModel] Starting annealing.\n",
"[MySAModel] Best fitness obtained: 3398.6263568993063\n",
"[MySAModel] Improvement over greedy heuristic: 0.00%\n",
"[*] [Node] 280, [Best] 3398.6263568993063\n",
"[*] Running for: 0.05 seconds\n",
"\n",
"[*] ./template/data/hard/dsj1000.tsp\n",
"[MySAModel] Starting annealing.\n",
"[MySAModel] Best fitness obtained: 24551747.27729817\n",
"[MySAModel] Improvement over greedy heuristic: 0.00%\n",
"[*] [Node] 1000, [Best] 24551747.27729817\n",
"[*] Running for: 0.33 seconds\n",
"\n",
"[*] ./template/data/simple/att48.tsp\n",
"[MySAModel] Starting annealing.\n",
"[MySAModel] Best fitness obtained: 39264.14564540566\n",
"[MySAModel] Improvement over greedy heuristic: 1.37%\n",
"[*] [Node] 48, [Best] 39264.14564540566\n",
"[*] Running for: 0.01 seconds\n",
"\n",
"[*] ./template/data/simple/ulysses16.tsp\n",
"[MySAModel] Starting annealing.\n",
"[MySAModel] Best fitness obtained: 76.04759446489814\n",
"[MySAModel] Improvement over greedy heuristic: 20.61%\n",
"[*] [Node] 16, [Best] 76.04759446489814\n",
"[*] Running for: 0.00 seconds\n",
"\n",
"[*] ./template/data/simple/st70.tsp\n",
"[MySAModel] Starting annealing.\n",
"[MySAModel] Best fitness obtained: 832.1275912241616\n",
"[MySAModel] Improvement over greedy heuristic: 4.06%\n",
"[*] [Node] 70, [Best] 832.1275912241616\n",
"[*] Running for: 0.01 seconds\n",
"\n"
]
}
],
"source": [
"model = MySAModel()\n",
"\n",
"print(\"Simulated Annealing\")\n",
"best_solutions, fitness_lists, times = TSP_Bench_ALL(tsp_path, model, T, stopping_T, alpha, max_it=1000)"
]
},
{
"cell_type": "code",
"execution_count": 37,
"metadata": {
"scrolled": false
},
"outputs": [
{
"data": {
"image/png": "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\n",
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"needs_background": "light"
},
"output_type": "display_data"
}
],
"source": [
"plot_results(best_solutions, times, \"Simulated Annealing Model\")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Conclusions"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.8.5"
}
},
"nbformat": 4,
"nbformat_minor": 4
}