{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "```{index} disjunctive programming\n", "```\n", "```{index} single: AMPL \n", "```\n", "\n", "# Extra material: Strip packing\n", "\n", "*Strip packing* (SP) refers to the problem of packing rectangles onto a two dimensional strip of fixed width. \n", "\n", "Many variants of this problem have been studied, the most basic is the pack a set of rectangles onto the shortest possible strip without rotation. Other variants allow rotation of the rectangles, require a packing that allows cutting the rectangles out of the strip with edge-to-edge cuts (guillotine packing), extends the strip to three dimensions, or extends the packing to non-rectangular shapes.\n", "\n", "The extensive study of strip packing problems is motivated by their many industrial applications including\n", "\n", "* placement of macro cells in semiconductor layouts,\n", "* wood and textile cutting operations,\n", "* laying out workstations in manufacturing facilities,\n", "* allocating communications bandwidth between two endpoints,\n", "* planning and scheduling $CO_2$ utilization for enhanced oil recovery,\n", "* scheduling allocations of a common resource.\n", "\n", "Finding optimal solutions to strip packing problems is combinatorially difficult. Strip packing belongs to a class of problems called \"NP-hard\" for which known solution algorithms require effort that grows exponentially with problem size. For that reason much research on strip packing has been directed towards practical heuristic algorithms for finding good, though not optimal, for industrial applications.\n", "\n", "Here we develop AMPL models to find optimal solutions to smaller but economically relevant problems. We use the problem of packing boxes onto shortest possible shelf of fixed width." ] }, { "cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [], "source": [ "# install dependencies and select solver\n", "%pip install -q amplpy pandas matplotlib\n", "\n", "SOLVER = \"highs\"\n", "\n", "from amplpy import AMPL, ampl_notebook\n", "\n", "ampl = ampl_notebook(\n", " modules=[\"highs\"], # modules to install\n", " license_uuid=\"default\", # license to use\n", ") # instantiate AMPL object and register magics" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Problem Statment\n", "\n", "Imagine a collection of $N$ boxes that are to placed on shelf. The shelf depth is $D$, and the dimensions of the boxes are $(w_i, d_i)$ for $i=0, \\ldots, N-1$. The boxes can be rotated, if needed, to fit on the shelf. How wide of a shelf is needed?\n", "\n", "We will start by creating a function to generate a table of $N$ boxes. For concreteness, we assume the dimensions are in millimeters." ] }, { "cell_type": "code", "execution_count": 2, "metadata": {}, "outputs": [ { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
wd
082103
17348
217153
37399
416785
5151172
654130
712694
\n", "
" ], "text/plain": [ " w d\n", "0 82 103\n", "1 73 48\n", "2 171 53\n", "3 73 99\n", "4 167 85\n", "5 151 172\n", "6 54 130\n", "7 126 94" ] }, "metadata": {}, "output_type": "display_data" }, { "name": "stdout", "output_type": "stream", "text": [ "Shelf Depth = 344\n" ] } ], "source": [ "import random\n", "import pandas as pd\n", "import matplotlib.pyplot as plt\n", "from matplotlib.patches import Rectangle\n", "\n", "# random seed\n", "random.seed(1842)\n", "\n", "\n", "# generate boxes\n", "def generate_boxes(N, max_width=200, max_depth=200):\n", " boxes = pd.DataFrame()\n", " boxes[\"w\"] = [random.randint(0.2 * max_width, max_width) for i in range(N)]\n", " boxes[\"d\"] = [random.randint(0.2 * max_depth, max_depth) for i in range(N)]\n", " return boxes\n", "\n", "\n", "N = 8\n", "boxes = generate_boxes(8)\n", "display(boxes)\n", "\n", "# set shelf width as a multiple of the deepest box\n", "D = 2 * boxes[\"d\"].max()\n", "print(\"Shelf Depth = \", D)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## A lower and upper bounds on shelf width\n", "\n", "A lower bound on the shelf width is established by from the area required to place all boxes on the shelf.\n", "\n", "$$W_{lb} = \\frac{1}{D}\\sum_{i=0}^{N-1} w_i d_i$$\n", "\n", "An upper bound is established by aligning the boxes along the front of the shelf without rotation. To set the stage for later calculations, the position of the rectangle on the shelf is defined by bounding box $(x_{i,1}, y_{i,1})$ and $(x_{i,2}, y_{i,2})$ extending from the lower left corner to the upper right corner. \n", "\n", "$$\n", "\\begin{align*}\n", "x_{i,2} & = x_{i,1} + w_i \\\\\n", "y_{i,2} & = y_{i,1} + d_i \\\\\n", "\\end{align*}\n", "$$\n", "\n", "An additional binary variable $r_i$ designates whether the rectangle has been rotated. The following cell performs these calculations to create and display a data frame showing the bounding boxes." ] }, { "cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [ { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
wdx1x2y1y2r
08210308201030
17348821550480
2171531553260530
373993263990990
4167853995660850
515117256671701720
65413071777101300
7126947718970940
\n", "
" ], "text/plain": [ " w d x1 x2 y1 y2 r\n", "0 82 103 0 82 0 103 0\n", "1 73 48 82 155 0 48 0\n", "2 171 53 155 326 0 53 0\n", "3 73 99 326 399 0 99 0\n", "4 167 85 399 566 0 85 0\n", "5 151 172 566 717 0 172 0\n", "6 54 130 717 771 0 130 0\n", "7 126 94 771 897 0 94 0" ] }, "metadata": {}, "output_type": "display_data" }, { "data": { "image/png": "iVBORw0KGgoAAAANSUhEUgAAA24AAAGJCAYAAADyj2B0AAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjcuMSwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/bCgiHAAAACXBIWXMAAA9hAAAPYQGoP6dpAABfZ0lEQVR4nO3dd3RU1d7G8WdSJj0TEkiDhCYtEorUIAEUpMi1wVXhooAgvCCogKJioSlEUQTkCui1gAU7NryogBJ66B1BOkpCkJRJCKTNef/gMjoSIIQkM5DvZ61Zztl7n3N+J5wsedinmAzDMAQAAAAAcFluzi4AAAAAAHBxBDcAAAAAcHEENwAAAABwcQQ3AAAAAHBxBDcAAAAAcHEENwAAAABwcQQ3AAAAAHBxBDcAAAAAcHEENwAAAABwcQQ3AECRxo8fL5PJpD/++KPUtjl37lyZTCYdOnTIoX39+vVq06aN/Pz8ZDKZtGXLljLfZ1HOHXNxlMXPBwCACyG4AQCcKj8/X3fffbfS0tI0bdo0vf/++6pevbqzy5IkrV69WuPHj1dGRkapb/vdd9+VyWTSunXrHNoNw1CdOnVkMpm0adMmh77CwkJVq1ZNN998c6nXcyG//vqrevXqpWrVqsnX11f169fXxIkTlZOT4zBu48aN6tq1qwIDAxUQEKDOnTsXGcD79+8vk8l0wc/vv/9eTkcGAFcXD2cXAACo2Pbv36/Dhw/rP//5jx588MFS3/7999+vXr16ycvL67LXXb16tSZMmKD+/fsrKCioVOuyWCySJKvV6tD+448/at++fUX2ffPNN/r99981ffr0Uq3lQo4ePaqWLVvKYrFo+PDhCg4O1po1azRu3Dht3LhRX3/9tSRp06ZNatu2raKiojRu3DjZbDbNmjVL7du317p161SvXj37Nv/v//5PnTp1ctiPYRgaMmSIatSooapVq5bLsQHA1YbgBgBwqtTUVEkq9WB0jru7u9zd3ctk21fiQsFt9uzZiomJ0a5du4rsi4yM1J133lkuNb7//vvKyMjQypUrdf3110uSBg8eLJvNpvfee0/p6emqVKmSnnvuOfn4+GjNmjUKCQmRJN13332qW7eunn76aX3xxRf2bcbFxSkuLs5hPytXrlROTo769OlTLscFAFcjLpUEgAoqKytLI0aMUI0aNeTl5aXQ0FDdcsst512el5GRYZ9xslgseuCBB867TE6Sfv/9dw0YMEBhYWHy8vLS9ddfr3feeeeiNfTv31/t27eXJN19990ymUzq0KFDkWO3bdsmk8mkb775xt62ceNGmUwm3XDDDQ5ju3XrplatWkm68D1uK1euVIsWLeTt7a3atWvrjTfecOgfP368Ro8eLUmqWbOm/VK+v2+nuD+fvzsX3LKysuxtR48e1cKFCzVq1Ch5eHg49O3bt09LlizRoEGD5OFRPv/uei44hoWFObRHRETIzc1NZrNZkrRixQp16tTJHtrOjWnfvr0WLlyo7Ozsi+5n/vz5MplM+te//lXKRwAA1w5m3ACgghoyZIg+//xzDR8+XDExMTp58qRWrlyp3bt3OwShe+65RzVr1lRCQoI2bdqkt956S6GhoXrppZfsY44fP67WrVvLZDJp+PDhqlKlihYtWqSBAwfKarVqxIgRRdbwf//3f6pataomT56sRx55RC1atDgvJJzTsGFDBQUFafny5br99tslnQ0Mbm5u2rp1q6xWqwIDA2Wz2bR69WoNHjz4gse+fft2de7cWVWqVNH48eNVUFCgcePGOey7R48e2rt3rz766CNNmzZNlStXliRVqVLFYVvF+fkUJTAwUJLjjNubb76pwMBA/etf/9Lo0aMd+ubMmSN3d/eLHpd09p7BzMzMi445Jzg4WG5uF/433A4dOuill17SwIEDNWHCBIWEhGj16tWaPXu2HnnkEfn5+UmScnNz5ePjc976vr6+ysvL044dO9S6desL1vvpp5+qTZs2qlGjRrHqBoAKyQAAVEgWi8UYNmzYBfvHjRtnSDIGDBjg0H7XXXcZISEhDm0DBw40IiIijD/++MOhvVevXobFYjFycnIMwzCMd99915BkHDx40D7m559/NiQZn3322SVr7t69u9GyZUv7co8ePYwePXoY7u7uxqJFiwzDMIxNmzYZkoyvv/76gvu88847DW9vb+Pw4cP2tl27dhnu7u7GX//X+PLLL5+3bkl+PkVJSUkxJBkvvPCCYRiGkZeXZ4SHhxuPPfaYYRiGER0dbbz44ouGYRjG6dOnjeDgYKNnz56X3O65n2dxPkUd1989//zzho+Pj8N6zzzzjMOY2NhYo27dukZBQYG9LTc314iOjjYkGZ9//vkFt//tt98akoxZs2ZdshYAqMiYcQOACiooKEhJSUk6duyYIiMjLzhuyJAhDsvx8fH68ssv7TNchmHoiy++0D333CPDMBwej9+lSxd9/PHH2rRpk2688cYrrjk+Pl7PPvusTp06JT8/P61cuVKTJ0/W4cOHtWLFCnXt2lUrVqyQyWRS27Zti9xGYWGhfvjhB915552Kjo62tzdo0EBdunTRf//738uq6VI/nwv5+z1uCxYs0PHjxzV06FBJUkBAgL3v008/VVpamoYNG3bJeho3bqzFixcXq/bw8PBLjqlRo4batWunnj17KiQkRN99950mT56s8PBwDR8+XJL00EMPaejQoRo4cKCeeOIJ2Ww2vfDCC0pOTpYknT59+oLbnz9/vjw9PXXPPfcUq2YAqKgIbgBQQU2ZMkX9+vVTVFSUmjVrpltvvVV9+/ZVrVq1HMb9NdxIUqVKlSRJ6enpCgwM1IkTJ5SRkaE333xTb775ZpH7OvcAkisVHx+vgoICrVmzRlFRUUpNTVV8fLx27typFStWSDp7+WRMTIyCg4OL3MaJEyd0+vRp1alT57y+evXqXXZwu9TP50K8vb1lNpvt97HNnj1bXbt2Ve3atSWdDW5/7WvQoIFuuummS9ZTqVKl857aWFIff/yxBg8erL1796patWqSzl5CarPZ9OSTT6p3794KCQnRkCFDdPToUb388suaN2+eJKl58+Z64oknNGnSJPn7+xe5/ezsbH399dfq0qWLw/1xAIDzEdwAoIK655577LNDP/74o15++WW99NJLWrBggbp162Yfd6EnMhqGIUmy2WySzj5FsF+/fkWObdSoUanU3Lx5c3l7e2v58uWKjo5WaGio6tatq/j4eM2aNUu5ublasWKF7rrrrlLZX3Fc6udzMYGBgbJardq1a5cSExP13Xff2fvOzbht3bpVa9eu1WuvvVasevLy8pSWllassVWqVLnoEzdnzZqlpk2b2kPbObfffrvmzp2rzZs320PipEmT9Pjjj2vnzp2yWCyKjY3V008/LUmqW7dukdv/6quveJokABQTwQ0AKrCIiAg99NBDeuihh5SamqobbrhBkyZNcghul1KlShUFBASosLCw1GZ6LsRsNqtly5ZasWKFoqOjFR8fL+nsTFxubq4+/PBDHT9+XO3atbtovT4+Pvr111/P69uzZ4/DsslkKt0D+BuLxSKr1arZs2erVq1a6tq1q73vXHCbPXu2/Pz8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lpYmSWrbNl5ZWVnasmWzJGn58kRVrlxZy5cvs29j+fJEtWvXQZI0ZUqCPvjgPf3733O0efNOPfLISPXvf5+WL0902O8HH8yT2WzWzz+v0syZcy5Y3wcfzJOHh4dWrlynqVNnaMaMV/XOO2/9Wf/TT+mLn37SW/95p8j6i+uDD+bJz89PK1YkafLkKZo0aaKWLFls73/qqdFasSJRn3/+tb777kctX75Mmzdvuug2LRbH4DZjxqu6++571aBBjEP7a69NU9++Dyg4OPiyai5tHk7dOwAAAFBODMNQVl5Wue83wBwgk8l02eudOnVKb745W2+9NVddu3aTJM2e/R8tXbpY7777th57bLQsFosaN26ixMRlatasuZYvX6ZHHhmpF16YoOzsbGVmZmr//n2Kj2+v3NxcvfTSZC1atEStW8dJkmrVqqXVq1fqrbfeULt27e37vu66OkpImHLJGqtVi9Irr0yTyWRSvXr1tGPHdr322jQNHDjobP3/maO5Y8eqa5dukpv7efUXV2xsIz377DhJUp06dTR79r/1889L1anTLcrOztbcuW9r7twPdPPNHSVJb789T7VqVbvoNoOC/rxU8sSJE/roow+0YsVabdmy2d6+cuUKbdq0UfPmzbev9803X2vZsp/UqVNn/fDDIs2Y8e9iH8eVILgBAACgQsjKy1KVVy3lvt8TozIV6BV42esdOLBf+fn5iou70d7m6emp5s1bas+e3fa2+Pj2Wr58mUaOfEyrVq3Q888n6PPPP9WqVSuVnp6myMhI1alTR7t27VROTo5uvfUWh/3k5eWpSZOmDm033NCsWDW2atXaIZS2ahWn6dOnqrCw0F7/jY0bX7T+4mjYsJHDcnh4hE6cSJV09ueUl5enFi1a2fuDg4NVt269i27zr5dKzpnzutq0aavY2EY6cGC/vX3GjFd122136LrrrrOvt2PHNsXGNtKOHdvUuHGTyzqOK0FwAwAAQIUQYA7QiVGZlx5YBvstS+3addC8ee9o27at8vT0VP369dWuXQctX75M6enpio8/O5OWnZ0tSfrqq+8UGVnVYRteXl4Oy76+fmVa8zkmk5vDPXGSlJ+ff944T0/Pv61nks1mu6J9WyxBys/PV3p6ut58c7beeed9SVJAQOD/Zir3a+HCb/TTTysc1tu+fZs6d+6qGTNeVWRkVbVu3UynT5/WJ58sUP369a+opovhHjcAAABUCCaTSYFegeX+KcllkpJUq1Ztmc1mrVmzyt6Wn5+vjRvXq379GHvbufvcXnttmj2knQtuy5cvs9/f1qBBjLy8vHT06BFdd911Dp+oqKgS1bhuXdLfltfquuvqyN3d3V7/qq1bL1h/lSpVlJKSbO+3Wq06dOjgZdVQq1ZteXp6av36P2tJT0/Xr7/uveh6QUFBkqRZs2YqLCxct9zSWZJksVhktWZq5szpatGipeLi2jist2vXTl1/fUNt375N1apFae3ajXr44RGaPv2Vy6r7cjHjBgAAALggPz8/DR48VGPGjFalSsGKjo7W1KlTlJOTowceGGgfV6lSJcXGNtJHH32o6dPP3m8VH99Offrco/z8fHuYCwgI0MiRj2v06JGy2Wxq06atrNZMrV69SoGBgbr//n6XXePRo0c0evQoPfjg/2nLlk2aNWumXnpp6p/1Dxqi0a+9poBGTRVdveZ59XfocLPef3+uune/TUFBQZowYazc3d0vqwZ/f3/17z9QY8aMVnBwiEJDQzV27DNyc7v4HJXFEiTp7MNHpk6dYW8PCAhURkaG3n9/rv7zn3cd1jl9+rQkyc3NTTk5ORo27GFJUuPGTfT99/+9rLovF8ENAAAAcFGTJr0om82mAQPuV1ZWlpo1a66FC39QpUqVHMbFx7fX1q1b7LNrwcHBatAgRqmpx1Wv3p/3eo0f/7wqV66iKVMSdPDgAQUFBalJkxv05JNPl6i+Pn366vTp02rbtqXc3d01fPijevDBwX/W/8Jkmf44rgED+xdZ/xNPjNGhQwd1113/kMVi0bhxz1/2jJskvfjiyzp1Kls9etymgIAAPfroY+e9o+3vzs24+fn56d57e9vbLRaLCgsLVblyFd1xh+MLunfu3KGYmOu1e/cu1a/fwB4ON2/epNhYx/vwSpvJ+PtFpRWQ1WqVxWLR9u2ZCg6+/BtHgYooK8+q+vMs+qVfpgLM/N4AAFxHQcEZWa0HFR1dU97e3s4up2KzFcq8Y7PyGjaV3C5vJs0Vvfvu20pOPqaoqGi99NJkbd68Q+np6brjjlv1zTeLVKVKlSLXO3PmjI4cOajAwJry8HA8J9PSrIqNtSgzM1OBgRf+OxUzbgAAAABQDNu3b1OHDjdr5crluvXWf6hNmxYqLCzUlCmvXjC0lRaCGwAAAAAUw6uvnr0X7vbb7yj3ffNUSQAAAABwcQQ3AAAAAHBxBDcAAAAAcHEENwAAAABwcQQ3AAAAAHBxBDcAAAAAcHEENwAAAABwcU4NbrNnz1ajRo0UGBiowMBAxcXFadGiRfb+M2fOaNiwYQoJCZG/v7969uyp48ePO2zjyJEj6t69u3x9fRUaGqrRo0eroKCgvA8FAAAAAMqMU4NbtWrV9OKLL2rjxo3asGGDbr75Zt1xxx3auXOnJGnkyJH69ttv9dlnnykxMVHHjh1Tjx497OsXFhaqe/fuysvL0+rVqzVv3jzNnTtXY8eOddYhAQAAAECp83Dmzm+77TaH5UmTJmn27Nlau3atqlWrprffflvz58/XzTffLEl699131aBBA61du1atW7fWjz/+qF27dmnJkiUKCwtTkyZN9Pzzz+vJJ5/U+PHjZTabnXFYAAAAAFCqXOYet8LCQn388cc6deqU4uLitHHjRuXn56tTp072MfXr11d0dLTWrFkjSVqzZo1iY2MVFhZmH9OlSxdZrVb7rF1RcnNzZbVaHT4AAACAq7vllg567LERpboNwzA0dOhghYcHy8vLpK1bt1zR9ovax+X2X+64isDpwW379u3y9/eXl5eXhgwZoi+//FIxMTFKSUmR2WxWUFCQw/iwsDClpKRIklJSUhxC27n+c30XkpCQIIvFYv9ERUWV7kEBAAAAV4kffvhe778/V19+uVCHDyfr+usbXvE2P/lkgcaPf77Y40szoPXvf5/uvvsuh7Zly36Wl5dJ48c/59A+derLql49Qnl5eaWy77Lk9OBWr149bdmyRUlJSRo6dKj69eunXbt2lek+x4wZo8zMTPvn6NGjZbo/AAAAwFUdOLBfERERiotro/DwcHl4XPndVMHBwQoICCiF6i6fxRIkqzXToW369Kny8vJSZuaf7QUFBZo9e6Yeeujhq+IWK6cHN7PZrOuuu07NmjVTQkKCGjdurBkzZig8PFx5eXnKyMhwGH/8+HGFh4dLksLDw897yuS55XNjiuLl5WV/kuW5DwAAAOAKFiz4XDfcECuLxUcRESHq2rWTTp06Ze+32WwaM+YJhYcHKzo6XM8/P95hfZvNpilTElS3bk1ZLD5q3ryxFiz4vMh9Pfhgf40c+bCOHDkiLy+T6tatcd6Y775bqNDQIBUWFkqStm7dIi8vk5555in7mCFDHlT//vfZl/86g3bq9GkNGNhfwcH+ql49QtOmTT2vhuXLE/Xvf8+Ql5dJXl4mHTp0qNjH+3dBQUEOAe2XX37R0qWLdf/9/R0C3RdffKaTJ09q0KAhF92eq3B6cPs7m82m3NxcNWvWTJ6enlq6dKm9b8+ePTpy5Iji4uIkSXFxcdq+fbtSU1PtYxYvXqzAwEDFxMSUe+0AAADAlUhOTtb99/dWv34DtHXrbi1evEx33tlDhmHYx3zwwTz5+flpxYokTZ48RZMmTdSSJYvt/VOmJOiDD97Tv/89R5s379Qjj4xU//73afnyxPP2N3XqDI0bN1HVqlXT4cPJWrVq/Xlj2raNV1ZWlrZs2SxJWr48UZUrV9by5cvsY5YvT1S7dh2KPKbRM2ZoxYrl+vzzr/Xddz9q+fJl2rx5k0MNrVvHacCAQTp8OFmHDyc73Mp0qeP9O4vFMbjNmPGq7r77XjVoEOPQ/tpr09S37wMKDg6+4LZciVOfKjlmzBh169ZN0dHRysrK0vz587Vs2TL98MMPslgsGjhwoEaNGqXg4GAFBgbq4YcfVlxcnFq3bi1J6ty5s2JiYnT//fdrypQpSklJ0bPPPqthw4bJy8vLmYcGAAAAV2MYUlZW+e83IEAymYo1NCUlWQUFBbrzzh6qXr26JKlhw1iHMbGxjfTss+MkSXXq1NHs2f/Wzz8vVadOtyg3N1cvvTRZixYtUevWZyc7atWqpdWrV+qtt95Qu3btHbZlsVjk7x8gd3f3C16xZrFY1LhxEyUmLlOzZs21fPkyPfLISL3wwgRlZ2crMzNT+/fvU3x8+/PWzc7O1tvffKO5776vm2/uKEl6++15qlWrmsP2zWazfH19i6zhYsdblKCgPy+VPHHihD766AOtWLFWW7ZstrevXLlCmzZt1Lx584vchityanBLTU1V3759lZycLIvFokaNGumHH37QLbec/UOYNm2a3Nzc1LNnT+Xm5qpLly6aNWuWfX13d3ctXLhQQ4cOVVxcnPz8/NSvXz9NnDjRWYcEAAAAV5WVJXMVS7nvNu9EplTMW3MaNWqsm27qqGbNYnXLLV3UqVNn9ejxT1WqVMk+pmHDRg7rhIdH6MSJs1eg7d+/Tzk5Obr1VsdQk5eXpyZNmpb4GOLj22v58mUaOfIxrVq1Qs8/n6DPP/9Uq1atVHp6miIjI1WnTp3z1jtwYL/y8vPVokVLe1twcLDq1q1X7H1f7HiL8tdLJefMeV1t2rRVbGwjHTiw394+Y8aruu22O3TdddcVuw5nc2pwe/vtty/a7+3trddff12vv/76BcdUr15d//3vf0u7NAAAAFxrAgLOhign7Le43N3dtWjRYq1Zs1pLlvyoWbNmaty4Z7RiRZJq1qwpSfL09HRYx2QyyWazSTo7wyVJX331nSIjqzqMu5Ir0tq166B5897Rtm1b5enpqfr166tduw5avnyZ0tPTi5xtKy0XO96iWCxBys/PV3p6ut58c7beeed9SVJAQOD/Zgf3a+HCb/TTTyvKrOay4NTgBgAAAJQbk6nYM1/OZDKZ1KbNjWrT5kY988xY1alTXV9//aVGjBh1yXUbNIiRl5eXjh49ct5lkVfi3H1ur702zR7S2rXroFdeeVHp6ekaMeKxIterVau2PD08tH79OkXXOBs809PT9euvex3Cnqen2f7wkyt17nVis2bNVFhYuG65pbOks5dkWq2Zmjlzulq0aKm4uDalsr/yQnADAAAAXMS6dUn/u3+rs6pUCdX69Uk6ceKE6tdvUKz1AwICNHLk4xo9eqRsNpvatGkrqzVTq1evUmBgoO6/v1+J6qpUqZJiYxvpo48+1PTp/5Ykxce3U58+9yg/P/+CM27+/v4aeMcdGvP0kwquXEWhoaEaO/YZubk5PiOxevUaWr8+SYcOHZK/v7+Cg4PPG1NcFkuQpLMPH5k6dYa9PSAgUBkZGXr//bn6z3/eLdG2nYngBgAAALiIgIBArVixXDNnTpfValV0dHW99NJUde3ardjbGD/+eVWuXEVTpiTo4MEDCgoKUpMmN+jJJ5++otri49tr69Yt9qdHBgcHq0GDGKWmHle9ehe+Z+3lRx6Rdc6b6tHjNgUEBOjRRx877z1rI0c+rgcf7KcmTWJ0+vRp7dlzUDVq1ChRnedm3Pz8/HTvvb3t7RaLRYWFhapcuYruuOOuC6ztukzGX58tWkFZrVZZLBZt356p4GDXnz4HXEFWnlX151n0S79MBZj5vQEAuI6CgjOyWg8qOrqmvL29nV1OxWYrlHnHZuU1bCq5uTu7Gqc5c+aMjhw5qMDAmvLwcDwn09Ksio21KDMz86Lvl3a597gBAAAAABwR3AAAAADAxRHcAAAAAMDFEdwAAAAAwMUR3AAAAHDNOfv4vQr/DD64DENX+khIghsAAACuKW5unpKk06dznFwJcNa5c/HcuVkSvMcNAAAA1xQ3N3eZzUE6cSJVkuTj4yvJ5NyiKiqjUDZJeblnJFNFfB2AodOnc3TiRKrM5iC5XcErEQhuAAAAuOb4+4crO1tKTT0b3kzkNuew2eT+xx8qNB+S3CrexX7nLo80m4Pk7x9+RdsiuAEAAOCaYzKZFBAQIZstVDZbvrPLqbhOZSt0SHelLtog+fk7uxqncHPzvKKZtnMIbgAAALhmubm5l8pfmlEyJrc8eR8+LE83swwPb2eXc1WrePOVAAAAAHCVIbgBAAAAgIsjuAEAAACAiyO4AQAAAICLI7gBAAAAgIsjuAEAAACAiyO4AQAAAICLI7gBAAAAgIsjuAEAAACAiyO4AQAAAICLI7gBAAAAgIsjuAEAAACAiyO4AQAAAICLI7gBAAAAgIsjuAEAAACAi3NqcEtISFCLFi0UEBCg0NBQ3XnnndqzZ4/DmA4dOshkMjl8hgwZ4jDmyJEj6t69u3x9fRUaGqrRo0eroKCgPA8FAAAAAMqMhzN3npiYqGHDhqlFixYqKCjQ008/rc6dO2vXrl3y8/Ozjxs0aJAmTpxoX/b19bV/LywsVPfu3RUeHq7Vq1crOTlZffv2laenpyZPnlyuxwMAAAAAZcGpwe377793WJ47d65CQ0O1ceNGtWvXzt7u6+ur8PDwIrfx448/ateuXVqyZInCwsLUpEkTPf/883ryySc1fvx4mc3mMj0GAAAAAChrLnWPW2ZmpiQpODjYof3DDz9U5cqV1bBhQ40ZM0Y5OTn2vjVr1ig2NlZhYWH2ti5dushqtWrnzp1F7ic3N1dWq9XhAwAAAACuyqkzbn9ls9k0YsQI3XjjjWrYsKG9/V//+peqV6+uyMhIbdu2TU8++aT27NmjBQsWSJJSUlIcQpsk+3JKSkqR+0pISNCECRPK6EgAAAAAoHS5THAbNmyYduzYoZUrVzq0Dx482P49NjZWERER6tixo/bv36/atWuXaF9jxozRqFGj7MtWq1VRUVElKxwAAAAAyphLXCo5fPhwLVy4UD///LOqVat20bGtWrWSJO3bt0+SFB4eruPHjzuMObd8ofvivLy8FBgY6PABAAAAAFfl1OBmGIaGDx+uL7/8Uj/99JNq1qx5yXW2bNkiSYqIiJAkxcXFafv27UpNTbWPWbx4sQIDAxUTE1MmdQMAAABAeXLqpZLDhg3T/Pnz9fXXXysgIMB+T5rFYpGPj4/279+v+fPn69Zbb1VISIi2bdumkSNHql27dmrUqJEkqXPnzoqJidH999+vKVOmKCUlRc8++6yGDRsmLy8vZx4eAAAAAJQKp864zZ49W5mZmerQoYMiIiLsn08++USSZDabtWTJEnXu3Fn169fXY489pp49e+rbb7+1b8Pd3V0LFy6Uu7u74uLidN9996lv374O730DAAAAgKuZU2fcDMO4aH9UVJQSExMvuZ3q1avrv//9b2mVBQAAAAAuxSUeTgIAAAAAuDCCGwAAAAC4OIIbAAAAALg4ghsAAAAAuDiCGwAAAAC4OIIbAAAAALg4ghsAAAAAuDiCGwAAAAC4OIIbAAAAALg4ghsAAAAAuDiCGwAAAAC4OIIbAAAAALg4ghsAAAAAuDiCGwAAAAC4OIIbAAAAALg4ghsAAAAAuDiCGwAAAAC4OIIbAAAAALg4ghsAAAAAuDiCGwAAAAC4OIIbAAAAALg4ghsAAAAAuDiCGwAAAAC4OIIbAAAAALg4ghsAAAAAuDiCGwAAAAC4OI+SrpiRkaF169YpNTVVNpvNoa9v375XXBgAAAAA4KwSBbdvv/1Wffr0UXZ2tgIDA2Uymex9JpOJ4AYAAAAApahEl0o+9thjGjBggLKzs5WRkaH09HT7Jy0trbRrBAAAAIAKrUTB7ffff9cjjzwiX1/f0q4HAAAAAPA3JQpuXbp00YYNG6545wkJCWrRooUCAgIUGhqqO++8U3v27HEYc+bMGQ0bNkwhISHy9/dXz549dfz4cYcxR44cUffu3eXr66vQ0FCNHj1aBQUFV1wfAAAAALiCYt/j9s0339i/d+/eXaNHj9auXbsUGxsrT09Ph7G33357sbaZmJioYcOGqUWLFiooKNDTTz+tzp07a9euXfLz85MkjRw5Ut99950+++wzWSwWDR8+XD169NCqVaskSYWFherevbvCw8O1evVqJScnq2/fvvL09NTkyZOLe3gAAAAA4LJMhmEYxRno5la8yTmTyaTCwsISFXPixAmFhoYqMTFR7dq1U2ZmpqpUqaL58+frn//8pyTpl19+UYMGDbRmzRq1bt1aixYt0j/+8Q8dO3ZMYWFhkqQ5c+boySef1IkTJ2Q2my+5X6vVKovFou3bMxUcHFii2oGKJivPqvrzLPqlX6YCzPzeAACA85myrIqob1HyL5kyAvj7QlHS0qyKjbUoMzNTgYEX/hkV+1JJm81WrE9JQ5skZWZmSpKCg4MlSRs3blR+fr46depkH1O/fn1FR0drzZo1kqQ1a9YoNjbWHtqks5dyWq1W7dy5s8j95Obmymq1OnwAAAAAwFWV6B639957T7m5uee15+Xl6b333itRITabTSNGjNCNN96ohg0bSpJSUlJkNpsVFBTkMDYsLEwpKSn2MX8Nbef6z/UVJSEhQRaLxf6JiooqUc0AAAAAUB5KFNweeOAB++zYX2VlZemBBx4oUSHDhg3Tjh079PHHH5do/csxZswYZWZm2j9Hjx4t830CAAAAQEmV6AXchmE4vHT7nN9++00Wi+Wytzd8+HAtXLhQy5cvV7Vq1ezt4eHhysvLU0ZGhsOs2/HjxxUeHm4fs27dOoftnXvq5Lkxf+fl5SUvL6/LrhMAAAAAnOGyglvTpk1lMplkMpnUsWNHeXj8uXphYaEOHjyorl27Fnt7hmHo4Ycf1pdffqlly5apZs2aDv3NmjWTp6enli5dqp49e0qS9uzZoyNHjiguLk6SFBcXp0mTJik1NVWhoaGSpMWLFyswMFAxMTGXc3gAAAAA4JIuK7jdeeedkqQtW7aoS5cu8vf3t/eZzWbVqFHDHrCKY9iwYZo/f76+/vprBQQE2O9Js1gs8vHxkcVi0cCBAzVq1CgFBwcrMDBQDz/8sOLi4tS6dWtJUufOnRUTE6P7779fU6ZMUUpKip599lkNGzaMWTUAAAAA14TLCm7jxo2TJNWoUUP33nuvvL29r2jns2fPliR16NDBof3dd99V//79JUnTpk2Tm5ubevbsqdzcXHXp0kWzZs2yj3V3d9fChQs1dOhQxcXFyc/PT/369dPEiROvqDYAAAAAcBXFfo9bUTZs2KDdu3dLkmJiYtSsWbNSK6w88R434PLxHjcAAHApvMft0or7HrcSPZzk999/V69evbRq1Sr7Q0MyMjLUpk0bffzxxw4PGAEAAAAAXJkSvQ5g4MCBys/P1+7du5WWlqa0tDTt3r1bNptNDz74YGnXCAAAAAAVWolm3BITE7V69WrVq1fP3lavXj3NnDlT8fHxpVYcAAAAAKCEM25RUVHKz88/r72wsFCRkZFXXBQAAAAA4E8lCm4vv/yyHn74YW3YsMHetmHDBj366KN65ZVXSq04AAAAAEAJL5Xs37+/cnJy1KpVK/tLuAsKCuTh4aEBAwZowIAB9rFpaWmlUykAAAAAVFAlCm7Tp08v5TIAAAAAABdSouDWr1+/0q4DAAAAAHABJbrHTZL279+vZ599Vr1791ZqaqokadGiRdq5c2epFQcAAAAAKGFwS0xMVGxsrJKSkrRgwQJlZ2dLkrZu3apx48aVaoEAAAAAUNGVKLg99dRTeuGFF7R48WKZzWZ7+80336y1a9eWWnEAAAAAgBIGt+3bt+uuu+46rz00NFR//PHHFRcFAAAAAPhTiYJbUFCQkpOTz2vfvHmzqlatesVFAQAAAAD+VKLg1qtXLz355JNKSUmRyWSSzWbTqlWr9Pjjj6tv376lXSMAAAAAVGglCm6TJ09W/fr1FRUVpezsbMXExCg+Pl5t2rTRs88+W9o1AgAAAECFVqL3uJnNZv3nP//R2LFjtX37dmVnZ6tp06aqU6dOadcHAABcSHp6unJycpxdBsqBr6+vKlWq5OwyAPxPsYPbqFGjLtr/16dJvvrqqyWvCAAAuKT09HSNnTRWJ7NPOrsUlIMQ/xBNfGYi4Q1wEcUObps3b3ZY3rRpkwoKClSvXj1J0t69e+Xu7q5mzZqVboUAAMAl5OTk6GT2SXk39pZPkI+zy0EZOp1xWie3nlROTg7BDXARxQ5uP//8s/37q6++qoCAAM2bN8/+y5yenq4HHnhA8fHxpV8lAABwGT5BPvIL8XN2GShjZ3TG2SUA+IsSPZxk6tSpSkhIcPgXmEqVKumFF17Q1KlTS604AAAAAEAJg5vVatWJEyfOaz9x4oSysrKuuCgAAAAAwJ9KFNzuuusuPfDAA1qwYIF+++03/fbbb/riiy80cOBA9ejRo7RrBAAAAIAKrUSvA5gzZ44ef/xx/etf/1J+fv7ZDXl4aODAgXr55ZdLtUAAAAAAqOhKFNx8fX01a9Ysvfzyy9q/f78kqXbt2vLz40ZlAAAAAChtJQpu5/j5+alRo0alVQsAAAAAoAgluscNAAAAAFB+CG4AAAAA4OIIbgAAAADg4ghuAAAAAODiCG4AAAAA4OKcGtyWL1+u2267TZGRkTKZTPrqq68c+vv37y+TyeTw6dq1q8OYtLQ09enTR4GBgQoKCtLAgQOVnZ1djkcBAAAAAGXLqcHt1KlTaty4sV5//fULjunatauSk5Ptn48++sihv0+fPtq5c6cWL16shQsXavny5Ro8eHBZlw4AAAAA5eaK3uN2pbp166Zu3bpddIyXl5fCw8OL7Nu9e7e+//57rV+/Xs2bN5ckzZw5U7feeqteeeUVRUZGlnrNAAAAAFDeXP4et2XLlik0NFT16tXT0KFDdfLkSXvfmjVrFBQUZA9tktSpUye5ubkpKSnpgtvMzc2V1Wp1+AAAAACAq3Lp4Na1a1e99957Wrp0qV566SUlJiaqW7duKiwslCSlpKQoNDTUYR0PDw8FBwcrJSXlgttNSEiQxWKxf6Kiosr0OAAAAADgSjj1UslL6dWrl/17bGysGjVqpNq1a2vZsmXq2LFjibc7ZswYjRo1yr5stVoJbwAAAABclkvPuP1drVq1VLlyZe3bt0+SFB4ertTUVIcxBQUFSktLu+B9cdLZ++YCAwMdPgAAAADgqq6q4Pbbb7/p5MmTioiIkCTFxcUpIyNDGzdutI/56aefZLPZ1KpVK2eVCQAAAAClyqmXSmZnZ9tnzyTp4MGD2rJli4KDgxUcHKwJEyaoZ8+eCg8P1/79+/XEE0/ouuuuU5cuXSRJDRo0UNeuXTVo0CDNmTNH+fn5Gj58uHr16sUTJQEAAABcM5w647ZhwwY1bdpUTZs2lSSNGjVKTZs21dixY+Xu7q5t27bp9ttvV926dTVw4EA1a9ZMK1askJeXl30bH374oerXr6+OHTvq1ltvVdu2bfXmm28665AAAAAAoNQ5dcatQ4cOMgzjgv0//PDDJbcRHBys+fPnl2ZZAAAAAOBSrqp73AAAAACgIiK4AQAAAICLI7gBAAAAgIsjuAEAAACAiyO4AQAAAICLI7gBAAAAgIsjuAEAAACAiyO4AQAAAICLc+oLuAEAAOCa8nPzlZyc7Owyis3X11eVKlVydhlAmSG4AQAAwEFeTp727d+nhNcT5OXl5exyiiXEP0QTn5lIeMM1i+AGAAAABwW5BcpXvsyNzKoU7vpB6HTGaZ3celI5OTkEN1yzCG4AAAAokrfFW34hfs4uo1jO6IyzSwDKFA8nAQAAAAAXR3ADAAAAABdHcAMAAAAAF0dwAwAAAAAXR3ADAAAAABdHcAMAAAAAF0dwAwAAAAAXR3ADAAAAABdHcAMAAAAAF0dwAwAAAAAXR3ADAAAAABdHcAMAAAAAF0dwAwAAAAAXR3ADAAAAABdHcAMAAAAAF0dwAwAAAAAXR3ADAAAAABfn1OC2fPly3XbbbYqMjJTJZNJXX33l0G8YhsaOHauIiAj5+PioU6dO+vXXXx3GpKWlqU+fPgoMDFRQUJAGDhyo7OzscjwKAAAAAChbHs7c+alTp9S4cWMNGDBAPXr0OK9/ypQpeu211zRv3jzVrFlTzz33nLp06aJdu3bJ29tbktSnTx8lJydr8eLFys/P1wMPPKDBgwdr/vz5l11PSsoxnT6ddcXHdTXz9fVVpUqVnF0GAAAAgL9wanDr1q2bunXrVmSfYRiaPn26nn32Wd1xxx2SpPfee09hYWH66quv1KtXL+3evVvff/+91q9fr+bNm0uSZs6cqVtvvVWvvPKKIiMjL6uesS+Pk9nL/coO6ioX4h+iic9MJLwBAAAALsSpwe1iDh48qJSUFHXq1MneZrFY1KpVK61Zs0a9evXSmjVrFBQUZA9tktSpUye5ubkpKSlJd911V5Hbzs3NVW5urn3ZarVKkrwbessS6V9GR+T6Tmec1smtJ5WTk0NwAwAAAFyIywa3lJQUSVJYWJhDe1hYmL0vJSVFoaGhDv0eHh4KDg62jylKQkKCJkyYcF67t8VbfiF+V1r6Ve2Mzji7BMAlpaenKycnx9lllAsumQYAwPW4bHArS2PGjNGoUaPsy1arVVFRUU6sCIArS09P19hJY3Uy+6SzSykXXDINAIDrcdngFh4eLkk6fvy4IiIi7O3Hjx9XkyZN7GNSU1Md1isoKFBaWpp9/aJ4eXnJy8ur9IsGcE3KycnRyeyT8m7sLZ8gH2eXU6a4ZBoAANfkssGtZs2aCg8P19KlS+1BzWq1KikpSUOHDpUkxcXFKSMjQxs3blSzZs0kST/99JNsNptatWrlrNIBXKN8gnwqxOXUXDINAIDrcWpwy87O1r59++zLBw8e1JYtWxQcHKzo6GiNGDFCL7zwgurUqWN/HUBkZKTuvPNOSVKDBg3UtWtXDRo0SHPmzFF+fr6GDx+uXr16XfYTJQEAACSpQXgtPdN1yAX7F2xZrAVbFpdjRSiO/Nx8JScnO7sM/I1bdpYiLj0MxeDU4LZhwwbddNNN9uVz953169dPc+fO1RNPPKFTp05p8ODBysjIUNu2bfX999/b3+EmSR9++KGGDx+ujh07ys3NTT179tRrr71W7scCAAAA58jLydO+/fuU8HoCt8O4GN/8fP1XUkZGuiwBgc4u56rm1ODWoUMHGYZxwX6TyaSJEydq4sSJFxwTHBxcopdtAwAAXMq8tV/pcNoxh7aTpzKcUwwuqCC3QPnKl7mRWZXCuT/XlZiOZ0rfSzk5p2VxdjFXOZe9xw0AAMDZfstI0d7UQ84uA8XEq51cj+1MnrNLuGYQ3AAAAC5gaHxvBXj7Ka8gTwf++E0LdyzTzuR9l14RAEqZm7MLAAAAcFXBfhZ5unvIz8tXsVXr6snODyr+umbOLgtABcSMGwAAwF/YbDbtTN6nDYd36HjWH/I1++jW69upVuUouZncdF/L27Xu0DblFuQ7u1QAFQjBDQAA4C/2pB5Swg9vOrRt+32Ppv1zjPzMPvIz+6hOlRrakfyrkyoEUBER3AAADngXEi4kOTlZBfkFzi7DKXLyzui49Q/VqhwlSQrw5gEYAMoXwQ0AYMe7kHAxZ3LO6ODRg7LkWeSnaze41AipqkMnf3do8zV7Kzywsn3Zeia7vMsCUMER3AAAdrwLCReTdjhN+YfyVVB4bc+69WnxD/mafbRy30YdSU9WgLefbr2+nXzNPpLOhjZeEQCgvBHcAADn4V1IKEpOeo6zSyg31YMjVb1l5HntBYUFenv1F8q/xsMrANdDcAMAAPiLj9Z/p7haTRUTUVvBvhb5mL1lPZ2tPccPauGOZTqcdszZJQKogAhuAAAAf3Hg5G86cPI3Z5cBAA54ATcAAAAAuDiCGwAAAAC4OIIbAAAAALg47nEDAABAmQrxC9LtjW5WbGRdVfIN1Jn8XKVmndSGIzv17fafnV0ecFUguAEAAKDM1AmtrtGdBtjfgydJnu4eCvD2k7+XL8ENKCaCGwAAAMqEr9lbj3S4X75mHxXaCvXz3nXafmyv8gryFRYQoghLFWeXCFw1CG4AAAAoEzfVaaVKvoGSpAVbFuvrbT/Z+7Y7qyjgKkVwAwAAQJloGtXA/t1kclPCHSMVFlBZ1jPZWn1gs77cukT5hQVOrBC4evBUSQAAAJSJqkFh9u//bNpZUZUiZPbwVGX/Srq90c0aeXM/J1YHXF0IbgAAACgTvmZv+/fs3BzNXv6xZi//WNm5OZKkRlXr6YaoGGeVB1xVCG4AAAAoE/mFhfbvS39Zo1UHNmnVgU36ac9ae3vDyDrOKA246hDcAAAAUCZOnkq3f//jVMaf37P/bPfx9CrPkoCrFsENAAAAZeLX1MP27yF+QUV+P3kqsxwrAq5ePFUSAAAAZeLnX9epXZ3mcjO5qWO91krOTJUk3VyvtX3M+sO8GAAoDoKbk3m4uevW69vpxto3qEpAsHLz87Qn9aC+2rJUh9J+d3Z5AAAAJbb/xBH9d8dy/SO2gwK8/TS0XW+H/m+3/6zDacecVB1wdSG4OZGbyU2PdxrgcFOu2d1TzaMbqlHVepq65F3tTN7nxAoBAACuzMcb/6vfMlJ0S/02qhoULkn6LSNZP+5erdUHNju5OuDqQXBzok714+yh7Wh6sr7YvFg1QiJ1Z+NOMrt7anDbe/TYFy+pwFZ4iS0BuBZUCwrXbbEdVCOkqoJ8A+XlYdbpvDM6knZMy35drzUHtzi7RAAokZX7N2nl/k3OLgO4qhHcnKjjX67vfmv1F9p/4og2HNmhWpWj1KhqPYX4BalpVAOtP7zDiVUCKC/VgyN0Y+0bHNoCvP10fWQdXR9ZR5X9K+nb7T87qToAAOBMBDcn8TP7qGpQmCSpoLBAB/44au/bm3pYjarWkyTVC6tJcAMqiOzc0/ppT5L2HD+gjNNZ8jP7qOv18aobWkOS1KXBjQQ3ALgGTfvnU6riH3zRMZO+n6PdKQfKqSK4Ipd+HcD48eNlMpkcPvXr17f3nzlzRsOGDVNISIj8/f3Vs2dPHT9+3IkVF99ffzmzc3NkGIZ92Xomu8hxAK5tW3//Re+s+UKrDmzWzuR9Wnd4u+au/dLe7827jgCgwuLWGbj8jNv111+vJUuW2Jc9PP4seeTIkfruu+/02WefyWKxaPjw4erRo4dWrVrljFIvi5eHp/37338RCwoL/jLOXG41VUTp6enKyclxdhlXpez8LEnSsWPH5O+Z5eRqylZycrIK8gsuPbAUmWSSxSdAN9f985LqXSn7y7UGAED5eO3nD+Tp7vjX8khLqB688Z+SpPQcqw6cOFrUqqhAXD64eXh4KDw8/Lz2zMxMvf3225o/f75uvvlmSdK7776rBg0aaO3atWrduvV567iS3IJ8+3ePv/2i/nU5tyCv3GqqaNLT0zV20lidzD7p7FKuSgVu+VJT6bkpz8nD5nnpFa5iZ3LO6ODRg7LkWeQnvzLf3/juw3Rdler2ZZth05bfftFbqz4r830DAMrfwZO/ndfWumZj+/ef9yap0LCVZ0lwQS4f3H799VdFRkbK29tbcXFxSkhIUHR0tDZu3Kj8/Hx16tTJPrZ+/fqKjo7WmjVrLhrccnNzlZuba1+2Wq1legxFOZGdZv/u7+UrN5ObbP/7hQzyCShyHEpXTk6OTmaflHdjb/kE+Ti7nKtOvpEnnZKC2gbJ03RtzwynHU5T/qF8h9nw8mQYhmw2m0wmk1P2X9E93vEBNYlqYF8e/eXLSs484cSKAFzrvDw81fZ/D6sqsBXqpz1JTq4IrsClg1urVq00d+5c1atXT8nJyZowYYLi4+O1Y8cOpaSkyGw2KygoyGGdsLAwpaSkXHS7CQkJmjBhQhlWfmmn8k7r94zjqhoUJg83d9WqXE37ThyRJF1XJdo+bs/xg84qscLwCfKRX0jZz6Jca/JtHtIpyS/YV55u1/a9Vznp5Xs57durv5Cf2VchfhZ1rBenumE11Lx6QwX7WTR24cxyraWia1OrqUNoA4DycGOtG+RrPvuPyhsP71DG6fKfZIDrceng1q1bN/v3Ro0aqVWrVqpevbo+/fRT+fiUfIZkzJgxGjVqlH3ZarUqKirqimotiaV71qpvqzskSQPb/FNfbP5RNUKq2p8oefJUhjYf3V2uNeXn5is5Oblc9+kszrhvCSiOo+l//uPT+sM7NKf3eJk9PFWrcpTCAysrxfqHE6urOPy9fHVfy9tkM2wqtNnOu/8EAMpKx/px9u+Lf1njxErgSq6q/wsFBQWpbt262rdvn2655Rbl5eUpIyPDYdbt+PHjRd4T91deXl7y8nL+DMGSX9bohqgYNYyso6hK4Rpxc197X15hvt5c+Wm5PkEoLydP+/bvU8LrCS7x8ylr5X3fEnApnu4eyi/ickxDfz519ty/wKLs3d/ydgV6++unPWsVW7UuT/kFUC7qhtZQ9eBISWf/Ie+X47wCAGddVcEtOztb+/fv1/33369mzZrJ09NTS5cuVc+ePSVJe/bs0ZEjRxQXF3eJLbkGm2HTK0ve0a3Xt9ONtW9QlYBg5ebnaW/qIX25ZYkOpf1ervUU5BYoX/kyNzKrUnilct23Mzj7viXg757/xyPad+KI9qYe0slTGQr09len+nH2p8vmFuTpWEaqk6usGBpVrasba9+gtFOZ+mjDfxVbta6zSwJQQXT6y2zbkl9WO7ESuBqXDm6PP/64brvtNlWvXl3Hjh3TuHHj5O7urt69e8tisWjgwIEaNWqUgoODFRgYqIcfflhxcXEu/0TJvyqwFeqb7T/rGxd6qa63xbtC3PNV3vctAZfi5WlWh7ot1aFuyyL7P1r/nc4U5BbZh9Lj5WHWA3E9JElz136p0/lnnFwRgIoi0NtPLarHSpJy8k5r5f5NTq4IrsSlg9tvv/2m3r176+TJk6pSpYratm2rtWvXqkqVKpKkadOmyc3NTT179lRubq66dOmiWbNmOblqACiZ/+5YrqZRDVQ1KEwB3n4yyaT0HKv2nTispb+s0Z7UQ84usUK454auquIfrKSDW7Xp6C5nlwOgAulQt5X9ftqV+zfxWig4cOng9vHHH1+039vbW6+//rpef/31cqoIAMrO4l9WazGXxThVhKWKbqnfRtm5OZqX9LWzywFQgZhMJt1ct5V9eQkPJcHfuHRwAwCgPAX5BMjNzU3+Xr6a1WtskWNevmu0Dqcd0zPfTC/f4gBc05pWa6DK/mefMbDz2K86lsk9zXBEcAMAAACcbNPRXbpv7hPOLgMujOAGAMD/HLee1Pvrvjmv/a7GneTv5StJ+mbbT/ot43h5lwYAqOAIbgAA/E9aTqZ+2LXyvPauMW3twW3F/o1KzjxR3qUBACo4N2cXAAAAAAC4OGbcgAquenCkWtdsrHphNVXZr5ICvf2Uk39G+04c0Xfbl/EIekDSyM9fdHYJAIAKjuAGVHA312utjvUcX1of6O6vG6Ji1KRqfb227ANtOLLDSdUBAABAIrjBSfzMPuresL3qhNZQrcrV5OVhliQt37dBb6781MnVVTwZOVYt+3W99qYelJ/ZV3c16aRIS6jc3NzUp+U/CG4AAABORnCDU4T4B+n2Rjc7uwxIWrV/kz5c963yCvPtbb9nHNfkO0ZKkqr4ByvQ20/WM6ecVSIAAECFR3CDUxQUFmp3ygH9mnpIgd7+6lC3pbNLqrD2FnEPW4r1D4fl3IL888YAAACg/BDc4BTHMlM16fs5ks7eY9VBBDdX0qJ6rP37LykHlFuQ58RqAAAAwOsAADioEVJVfVvfIUnKK8zXB+u/dXJFAAAAYMYNgF3d0Bp6vNMD8jX7qMBWqFmJ83Xo5O/OLgsAAKDCI7gBkCQ1jKyjETf1k7enWXmF+fr3sg+16eguZ5cFAAAAEdwASGoefb2Gte8jT3cPncnP1bSf5mln8j5nlwUAAID/IbgBFVzL6rEa1v5fcndzl82w6cstS5RfWKC6oTXsYw78cVQFtkLnFQkAAFDBEdyACq5JVAO5u7lLktxMburdovt5Y0Z8nqA/stPLuzQAAAD8D8ENTmF291TjavUlSTWCI+3tlf0q2R9Ff+CPozp5KsMZ5QEAAAAuheAGpwj08dejN91/XntMRG3FRNSWJL2x8hOt2LexvEurcN5c+aneXPmps8sAAADARfAeNwAAAABwccy4wSn+yE7XfXOfcHYZAAAAwFWBGTcAAAAAcHEENwAAAABwcQQ3AAAAAHBxBDcAAAAAcHEENwAAAABwcQQ3AAAAAHBxBDcAAAAAcHEENwAAAABwcQQ3AAAAAHBx10xwe/3111WjRg15e3urVatWWrdunbNLAgAAAIBScU0Et08++USjRo3SuHHjtGnTJjVu3FhdunRRamqqs0sDAAAAgCt2TQS3V199VYMGDdIDDzygmJgYzZkzR76+vnrnnXecXRoAAAAAXDEPZxdwpfLy8rRx40aNGTPG3ubm5qZOnTppzZo1Ra6Tm5ur3Nxc+3JmZqYkKSslu2yLdXHW4zmyFZpkTc6Ruy3T2eWUuYp2vKUt38iTzkhpR63yNJmdXU6ZqkjnSkU6Vlw+zo+K42r7s77a6q1ITKnZskrKtGbLK83q7HJcUkbG2Z+LYRgXHWcyLjXCxR07dkxVq1bV6tWrFRcXZ29/4oknlJiYqKSkpPPWGT9+vCZMmFCeZQIAAADABR09elTVqlW7YP9VP+NWEmPGjNGoUaPsyxkZGapevbqOHDkii8XixMpQkVmtVkVFReno0aMKDAx0djmowDgX4So4F+EqOBdRlgzDUFZWliIjIy867qoPbpUrV5a7u7uOHz/u0H78+HGFh4cXuY6Xl5e8vLzOa7dYLPwywukCAwM5D+ESOBfhKjgX4So4F1FWijN5dNU/nMRsNqtZs2ZaunSpvc1ms2np0qUOl04CAAAAwNXqqp9xk6RRo0apX79+at68uVq2bKnp06fr1KlTeuCBB5xdGgAAAABcsWsiuN177706ceKExo4dq5SUFDVp0kTff/+9wsLCirW+l5eXxo0bV+Tlk0B54TyEq+BchKvgXISr4FyEK7jqnyoJAAAAANe6q/4eNwAAAAC41hHcAAAAAMDFEdwAAAAAwMUR3AAAAADAxVX44Pb666+rRo0a8vb2VqtWrbRu3Tpnl4RrSEJCglq0aKGAgACFhobqzjvv1J49exzGnDlzRsOGDVNISIj8/f3Vs2fP814of+TIEXXv3l2+vr4KDQ3V6NGjVVBQUJ6HgmvMiy++KJPJpBEjRtjbOBdRXn7//Xfdd999CgkJkY+Pj2JjY7VhwwZ7v2EYGjt2rCIiIuTj46NOnTrp119/ddhGWlqa+vTpo8DAQAUFBWngwIHKzs4u70PBVaywsFDPPfecatasKR8fH9WuXVvPP/+8/vrcPs5FuJIKHdw++eQTjRo1SuPGjdOmTZvUuHFjdenSRampqc4uDdeIxMREDRs2TGvXrtXixYuVn5+vzp0769SpU/YxI0eO1LfffqvPPvtMiYmJOnbsmHr06GHvLywsVPfu3ZWXl6fVq1dr3rx5mjt3rsaOHeuMQ8I1YP369XrjjTfUqFEjh3bORZSH9PR03XjjjfL09NSiRYu0a9cuTZ06VZUqVbKPmTJlil577TXNmTNHSUlJ8vPzU5cuXXTmzBn7mD59+mjnzp1avHixFi5cqOXLl2vw4MHOOCRcpV566SXNnj1b//73v7V792699NJLmjJlimbOnGkfw7kIl2JUYC1btjSGDRtmXy4sLDQiIyONhIQEJ1aFa1lqaqohyUhMTDQMwzAyMjIMT09P47PPPrOP2b17tyHJWLNmjWEYhvHf//7XcHNzM1JSUuxjZs+ebQQGBhq5ubnlewC46mVlZRl16tQxFi9ebLRv39549NFHDcPgXET5efLJJ422bdtesN9msxnh4eHGyy+/bG/LyMgwvLy8jI8++sgwDMPYtWuXIclYv369fcyiRYsMk8lk/P7772VXPK4p3bt3NwYMGODQ1qNHD6NPnz6GYXAuwvVU2Bm3vLw8bdy4UZ06dbK3ubm5qVOnTlqzZo0TK8O1LDMzU5IUHBwsSdq4caPy8/MdzsP69esrOjrafh6uWbNGsbGxDi+U79Kli6xWq3bu3FmO1eNaMGzYMHXv3t3hnJM4F1F+vvnmGzVv3lx33323QkND1bRpU/3nP/+x9x88eFApKSkO56LFYlGrVq0czsWgoCA1b97cPqZTp05yc3NTUlJS+R0Mrmpt2rTR0qVLtXfvXknS1q1btXLlSnXr1k0S5yJcj4ezC3CWP/74Q4WFhQ5/AZGksLAw/fLLL06qCtcym82mESNG6MYbb1TDhg0lSSkpKTKbzQoKCnIYGxYWppSUFPuYos7Tc31AcX388cfatGmT1q9ff14f5yLKy4EDBzR79myNGjVKTz/9tNavX69HHnlEZrNZ/fr1s59LRZ1rfz0XQ0NDHfo9PDwUHBzMuYhie+qpp2S1WlW/fn25u7ursLBQkyZNUp8+fSSJcxEup8IGN6C8DRs2TDt27NDKlSudXQoqoKNHj+rRRx/V4sWL5e3t7exyUIHZbDY1b95ckydPliQ1bdpUO3bs0Jw5c9SvXz8nV4eK5NNPP9WHH36o+fPn6/rrr9eWLVs0YsQIRUZGci7CJVXYSyUrV64sd3f3856Ydvz4cYWHhzupKlyrhg8froULF+rnn39WtWrV7O3h4eHKy8tTRkaGw/i/nofh4eFFnqfn+oDi2Lhxo1JTU3XDDTfIw8NDHh4eSkxM1GuvvSYPDw+FhYVxLqJcREREKCYmxqGtQYMGOnLkiKQ/z6WL/f85PDz8vAeJFRQUKC0tjXMRxTZ69Gg99dRT6tWrl2JjY3X//fdr5MiRSkhIkMS5CNdTYYOb2WxWs2bNtHTpUnubzWbT0qVLFRcX58TKcC0xDEPDhw/Xl19+qZ9++kk1a9Z06G/WrJk8PT0dzsM9e/boyJEj9vMwLi5O27dvd/gfw+LFixUYGHjeX36AC+nYsaO2b9+uLVu22D/NmzdXnz597N85F1EebrzxxvNei7J3715Vr15dklSzZk2Fh4c7nItWq1VJSUkO52JGRoY2btxoH/PTTz/JZrOpVatW5XAUuBbk5OTIzc3xr8Lu7u6y2WySOBfhgpz9dBRn+vjjjw0vLy9j7ty5xq5du4zBgwcbQUFBDk9MA67E0KFDDYvFYixbtsxITk62f3JycuxjhgwZYkRHRxs//fSTsWHDBiMuLs6Ii4uz9xcUFBgNGzY0OnfubGzZssX4/vvvjSpVqhhjxoxxxiHhGvLXp0oaBuciyse6desMDw8PY9KkScavv/5qfPjhh4avr6/xwQcf2Me8+OKLRlBQkPH1118b27ZtM+644w6jZs2axunTp+1junbtajRt2tRISkoyVq5cadSpU8fo3bu3Mw4JV6l+/foZVatWNRYuXGgcPHjQWLBggVG5cmXjiSeesI/hXIQrqdDBzTAMY+bMmUZ0dLRhNpuNli1bGmvXrnV2SbiGSCry8+6779rHnD592njooYeMSpUqGb6+vsZdd91lJCcnO2zn0KFDRrdu3QwfHx+jcuXKxmOPPWbk5+eX89HgWvP34Ma5iPLy7bffGg0bNjS8vLyM+vXrG2+++aZDv81mM5577jkjLCzM8PLyMjp27Gjs2bPHYczJkyeN3r17G/7+/kZgYKDxwAMPGFlZWeV5GLjKWa1W49FHHzWio6MNb29vo1atWsYzzzzj8HoTzkW4EpNh/OX18AAAAAAAl1Nh73EDAAAAgKsFwQ0AAAAAXBzBDQAAAABcHMENAAAAAFwcwQ0AAAAAXBzBDQAAAABcHMENAAAAAFwcwQ0AAAAAXBzBDQCAYpg7d66CgoIuOmb8+PFq0qTJRcccOnRIJpNJW7ZsKbXaAADXPoIbAADFcO+992rv3r2XtU7//v115513lk1BAIAKxcPZBQAAcDXw8fGRj4+Ps8sAAFRQzLgBACqshQsXKigoSIWFhZKkLVu2yGQy6amnnrKPefDBB3XfffcVeankiy++qLCwMAUEBGjgwIE6c+aMvW/8+PGaN2+evv76a5lMJplMJi1btszef+DAAd10003y9fVV48aNtWbNmjI9VgDA1Y3gBgCosOLj45WVlaXNmzdLkhITE1W5cmWHgJWYmKgOHTqct+6nn36q8ePHa/LkydqwYYMiIiI0a9Yse//jjz+ue+65R127dlVycrKSk5PVpk0be/8zzzyjxx9/XFu2bFHdunXVu3dvFRQUlNmxAgCubgQ3AECFZbFY1KRJE3tQW7ZsmUaOHKnNmzcrOztbv//+u/bt26f27duft+706dM1cOBADRw4UPXq1dMLL7ygmJgYe7+/v798fHzk5eWl8PBwhYeHy2w22/sff/xxde/eXXXr1tWECRN0+PBh7du3r8yPGQBwdSK4AQAqtPbt22vZsmUyDEMrVqxQjx491KBBA61cuVKJiYmKjIxUnTp1zltv9+7datWqlUNbXFxcsffbqFEj+/eIiAhJUmpqagmPAgBwrePhJACACq1Dhw565513tHXrVnl6eqp+/frq0KGDli1bpvT09CJn20qDp6en/bvJZJIk2Wy2MtkXAODqx4wbAKBCO3ef27Rp0+wh7VxwW7ZsWZH3t0lSgwYNlJSU5NC2du1ah2Wz2Wx/8AkAAFeC4AYAqNAqVaqkRo0a6cMPP7SHtHbt2mnTpk3au3fvBWfcHn30Ub3zzjt69913tXfvXo0bN047d+50GFOjRg1t27ZNe/bs0R9//KH8/PyyPhwAwDWK4AYAqPDat2+vwsJCe3ALDg5WTEyMwsPDVa9evSLXuffee/Xcc8/piSeeULNmzXT48GENHTrUYcygQYNUr149NW/eXFWqVNGqVavK+lAAANcok2EYhrOLAAAAAABcGDNuAAAAAODiCG4AAAAA4OIIbgAAAADg4ghuAAAAAODiCG4AAAAA4OIIbgAAAADg4ghuAAAAAODiCG4AAAAA4OIIbgAAAADg4ghuAAAAAODiCG4AAAAA4OL+H1H2CyHVA9vGAAAAAElFTkSuQmCC", "text/plain": [ "
" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "def pack_boxes_V0(boxes):\n", " soln = boxes.copy()\n", " soln[\"x1\"] = soln[\"w\"].cumsum() - soln[\"w\"]\n", " soln[\"x2\"] = soln[\"w\"].cumsum()\n", " soln[\"y1\"] = 0\n", " soln[\"y2\"] = soln[\"d\"]\n", " soln[\"r\"] = 0\n", " return soln\n", "\n", "\n", "def show_boxes(soln, D):\n", " \"\"\"Show bounding boxes on a diagram of the shelf.\"\"\"\n", " fig, ax = plt.subplots(1, 1, figsize=(14, 4))\n", " for i, x, y, w, h, r in zip(\n", " soln.index, soln[\"x1\"], soln[\"y1\"], soln[\"w\"], soln[\"d\"], soln[\"r\"]\n", " ):\n", " c = \"g\"\n", " if r:\n", " h, w = w, h\n", " c = \"r\"\n", " ax.add_patch(Rectangle((x, y), w, h, edgecolor=\"k\", facecolor=c, alpha=0.6))\n", " xc = x + w / 2\n", " yc = y + h / 2\n", " ax.annotate(\n", " i, (xc, yc), color=\"w\", weight=\"bold\", fontsize=12, ha=\"center\", va=\"center\"\n", " )\n", "\n", " W_lb = (soln[\"w\"] * soln[\"d\"]).sum() / D\n", " ax.set_xlim(0, 1.1 * soln[\"w\"].sum())\n", " ax.set_ylim(0, D * 1.1)\n", " ax.axhline(D, label=\"shelf depth $D$\", lw=0.8)\n", " ax.axvline(W_lb, label=\"lower bound $W_{lb}$\", color=\"g\", lw=0.8)\n", " ax.axvline(soln[\"x2\"].max(), label=\"shelf width $W$\", color=\"r\", lw=0.8)\n", " ax.fill_between([0, ax.get_xlim()[1]], [D, D], color=\"b\", alpha=0.1)\n", " ax.set_title(f\"shelf width $W$ = {soln['x2'].max():.0f}\")\n", " ax.set_xlabel(\"width\")\n", " ax.set_ylabel(\"depth\")\n", " ax.set_aspect(\"equal\")\n", " ax.legend(loc=\"upper right\")\n", "\n", "\n", "soln = pack_boxes_V0(boxes)\n", "display(soln)\n", "show_boxes(soln, D)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Modeling Strategy\n", "\n", "At this point the reader may have some ideas on how to efficiently pack boxes on the shelf. For example, one might start by placing the larger boxes to left edge of the shelf, then rotating and placing the smaller boxes with a goal of minimized the occupied with of the shelf. \n", "\n", "Modeling for optimization takes a different approach. The strategy is to describe constraints that must be satisfied for any solution to the problem, then let the solver find the a choice for the decision variables that minimizes width. The constraints include:\n", "\n", "* The bounding boxes must fit within the boundaries of the shelf, and to the left of vertical line drawn at $x = W$.\n", "* The boxes can be rotated 90 degrees.\n", "* The boxes must not overlap in either the $x$ or $y$ dimensions." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Version 1: An AMPL model to line up the boxes\n", "\n", "For this first AMPL model we look to reproduce a lineup of the boxes on the shelf. In the case the problem is to minimize $W$ where\n", "\n", "$$\n", "\\begin{align*}\n", "& \\min W \\\\\n", "\\text{subject to:}\\qquad\\qquad \\\\\n", "x_{i, 2} & = x_{i, 1} + w_i & \\forall i\\\\\n", "x_{i, 2} & \\leq W & \\forall i\\\\\n", "x_{i, 1}, x_{i, 2} & \\geq 0 & \\forall i \\\\\n", "\\\\\n", "[x_{i, 2} \\leq x_{j,1}] & \\veebar [ x_{j, 2} \\leq x_{i, 1}] & \\forall i < j \\\\\n", "\\\\\n", "\\end{align*}\n", "$$\n", "\n", "This first model does not consider rotation or placement of the boxes in the $y$ dimension, so those decisions are not included. \n", "\n", "The disjunctive constraints specify relationships between $x_{i,1}$ and $x_{i,2}$ to prevent overlapping positions of boxes on the shelf. The disjunctions require that either that box $i$ is to the left of box $j$ or that box $j$ is the left of box $i$. This is specified as an exclusive or disjunction because both conditions can be true at the same time. This disjunctive relationship must hold for every pair of boxes that are different from each other, but specifying $i$ doesn't overlap with $j$ assures $j$ doesn't overlap $i$. So it is only necessary to specify disjunctions for all pairs $i, j$ where $i < j$.\n", "\n", "The corresponding AMPL model is a direct implementation of this model. One feature of the implementation is the use of a set `PAIRS` to identify the disjunctions. Defining this set simplifies coding for the corresponding disjunction.\n" ] }, { "cell_type": "code", "execution_count": 4, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Overwriting pack_boxes_V1.mod\n" ] } ], "source": [ "%%writefile pack_boxes_V1.mod\n", "\n", "set BOXES;\n", "set PAIRS within {BOXES,BOXES};\n", "\n", "param w{BOXES};\n", "\n", "param W_ub;\n", "\n", "var W >= 0, <= W_ub;\n", "var x1{BOXES} >= 0, <= W_ub;\n", "var x2{BOXES} >= 0, <= W_ub;\n", "\n", "minimize minimize_width: W;\n", "\n", "s.t. bounding_box {i in BOXES}:\n", " x2[i] == x1[i] + w[i];\n", "s.t. width {i in BOXES}:\n", " x2[i] <= W;\n", "s.t. no_overlap {(i, j) in PAIRS}:\n", " (x2[i] <= x1[j] or x2[j] <= x1[i])\n", " and not\n", " (x2[i] <= x1[j] and x2[j] <= x1[i]);" ] }, { "cell_type": "code", "execution_count": 5, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "HiGHS 1.5.1: \b\b\b\b\b\b\b\b\b\b\b\b\bHiGHS 1.5.1: optimal solution; objective 896.9999999\n", "344603 simplex iterations\n", "73081 branching nodes\n", "absmipgap=0.000150937, relmipgap=1.68269e-07\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
wdx1x2y1y2r
0821030.082.001030
17348770.0843.00480
217153432.0603.00530
3739982.0155.00990
416785603.0770.00850
5151172281.0432.001720
654130843.0897.001300
712694155.0281.00940
\n", "
" ], "text/plain": [ " w d x1 x2 y1 y2 r\n", "0 82 103 0.0 82.0 0 103 0\n", "1 73 48 770.0 843.0 0 48 0\n", "2 171 53 432.0 603.0 0 53 0\n", "3 73 99 82.0 155.0 0 99 0\n", "4 167 85 603.0 770.0 0 85 0\n", "5 151 172 281.0 432.0 0 172 0\n", "6 54 130 843.0 897.0 0 130 0\n", "7 126 94 155.0 281.0 0 94 0" ] }, "metadata": {}, "output_type": "display_data" }, { "data": { "image/png": "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gqH471atWlWsmTlJOnjw4EUfCHL8+HH7DOJf5efnS5IKCgoc2itUqOBwierixYtVpUoV1a1bt8jtf/TRR/L397c/bAYAcGEENwAohwoLC5WdnW2/z0qSQkNDFRkZqdzc3Mvalru7u3r06KF58+Zp+/btql+/vkP/iRMnznsS45WIj4/Xa6+9pv379+vxxx+XJFWsWFH16tWzP8nxXKC7UL2dO3fW119/rSNHjtgvddy1a5d+/PFHh7HnnpqYkZFRavX/lcViUXJyshITE/X88887POExICBAu3bt0qJFi9S7d++LXnb5V6V5j1vt2rX1008/ac+ePQ6zZh9//LHc3NwuOpP66aefat26dXr11VeLfHLliRMntHjxYvXq1Uu+vr7FqhcAyjOCGwCUQ1lZWapSpYr++c9/qmHDhvL399fixYu1bt06TZky5bK399JLL+mXX35RixYtNHDgQMXExCgtLU0bN27U4sWLi33pXnHEx8dr4sSJOnr0qENAa9u2rd58801Vq1btvEv7/m78+PH64YcfFB8fr4cfflgFBQWaMWOGbrzxRm3dutU+rkmTJpKkZ599Vj179pSnp6duv/12e6C7UhaLRb/88ot8fHzUv39/h76AgACtXbtW0tmHfxRXad7jNmrUKC1cuFDx8fEaNmyYQkJCtGDBAi1cuFAPPfSQ/aE2y5Yt04QJE9SpUyeFhIRozZo1eu+999SlSxc99thjRW77008/VUFBAZdJAkAxEdwAoBzy9fXVww8/rJ9++knz58+XzWbTDTfcoJkzZ9qfang5wsLCtHbtWk2YMEHz58/XzJkzFRISohtvvPGS7zO7XK1atZK7u7t8fX3VsGFDe3t8fLzefPPNi862ndOgQQP9+OOPGjlypMaMGaMqVapo/PjxSk5OdghuzZo10wsvvKDZs2frhx9+kM1m08GDB0s1uElSr169znuYSkBAgKSzx/vX4yxLbdu21apVqzRu3DjNnDlTJ0+eVPXq1TVx4kQ9+eST9nGVK1eWu7u7XnnlFWVlZal69ep68cUX7S8SL8pHH32k0NDQq355LQBcL0xGce6eBgAAAAA4zfkXnQMAAAAAXArBDQAAAABcHMENAAAAAFwcwQ0AAAAAXBzBDQAAAABcHMENAAAAAFwc73GTZLPZdOzYMQUEBMhkMjm7HAAAAADlhGEYysrKUmRk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", "text/plain": [ "
" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "def pack_boxes_V1(boxes):\n", " # a simple upper bound on shelf width\n", " W_ub = boxes[\"w\"].sum()\n", "\n", " BOXES = list(boxes.index)\n", " PAIRS = [(i, j) for i in BOXES for j in BOXES if i < j]\n", "\n", " m = AMPL()\n", " m.read(\"pack_boxes_V1.mod\")\n", "\n", " m.set[\"BOXES\"] = BOXES\n", " m.set[\"PAIRS\"] = PAIRS\n", "\n", " m.param[\"w\"] = boxes[\"w\"]\n", " m.param[\"W_ub\"] = int(W_ub)\n", "\n", " m.solve(solver=SOLVER)\n", " assert m.solve_result == \"solved\", m.solve_result\n", "\n", " soln = boxes.copy()\n", " soln[\"x1\"] = m.var[\"x1\"].to_dict()\n", " soln[\"x2\"] = m.var[\"x2\"].to_dict()\n", " soln[\"y1\"] = 0\n", " soln[\"y2\"] = soln[\"y1\"] + soln[\"d\"]\n", " soln[\"r\"] = 0\n", " return soln\n", "\n", "\n", "soln = pack_boxes_V1(boxes)\n", "display(soln)\n", "show_boxes(soln, D)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Version 2: Rotating boxes\n", "\n", "Rotating the boxes is an option for packing the boxes more tightly on the shelf. The boxes can be placed either in their original orientation or in a rotated orientation. This introduces a second exclusive or disjunction to the model that determines the orientation of the bounding box. A boolean indicator variable $r_i$ tracks which boxes were rotated which is used in the `show_boxes` function to show which boxes have been rotated.\n", "\n", "$$\n", "\\begin{align*}\n", "& \\min W \\\\\n", "\\text{subject to:}\\qquad\\qquad \\\\\n", "x_{i, 2} & \\leq W & \\forall i\\\\\n", "x_{i, 1}, x_{i, 2} & \\geq 0 & \\forall i \\\\\n", "y_{i, 1} & = 0 & \\forall i \\\\\n", "\\\\\n", "[x_{i, 2} \\leq x_{j,1}] & \\veebar [ x_{j, 2} \\leq x_{i, 1}] & \\forall i < j \\\\\n", "\\\\\n", "\\begin{bmatrix}\n", "\\neg r_i \\\\\n", "x_{i,2} = x_{i,1} + w_i\\\\\n", "y_{i,2} = y_{i,1} + d_i\\\\\n", "\\end{bmatrix} & \\veebar \n", "\\begin{bmatrix}\n", "r_i \\\\\n", "x_{i,2} = x_{i,1} + d_i\\\\\n", "y_{i,2} = y_{i,1} + w_i\\\\\n", "\\end{bmatrix} & \\forall i < j\n", "\\end{align*}\n", "$$\n", "\n", "For this version of the model the boxes will be lined up against the edge of the shelf with $y_{i,1} = 0$. Decision variables are now included in the model for rotation $r$ to the $y$ dimension of the bounding boxes." ] }, { "cell_type": "code", "execution_count": 6, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Overwriting pack_boxes_V2.mod\n" ] } ], "source": [ "%%writefile pack_boxes_V2.mod\n", "\n", "set BOXES;\n", "set PAIRS within {BOXES,BOXES};\n", "\n", "param w{BOXES};\n", "param d{BOXES};\n", "\n", "param W_ub;\n", "\n", "var W >= 0, <= W_ub;\n", "var x1{BOXES} >= 0, <= W_ub;\n", "var x2{BOXES} >= 0, <= W_ub;\n", "var y1{BOXES} >= 0, <= W_ub;\n", "var y2{BOXES} >= 0, <= W_ub;\n", "var r{BOXES} binary;\n", "\n", "minimize minimize_width: W;\n", "\n", "s.t. width {i in BOXES}:\n", " x2[i] <= W;\n", "s.t. yloc {i in BOXES}:\n", " y1[i] == 0;\n", " \n", "s.t. rotate {i in BOXES}:\n", " r[i] == 0 ==> \n", " (x2[i] == x1[i] + w[i] and y2[i] == y1[i] + d[i])\n", " else\n", " (x2[i] == x1[i] + d[i] and y2[i] == y1[i] + w[i]);\n", "\n", "s.t. no_overlap {(i, j) in PAIRS}:\n", " (x2[i] <= x1[j] or x2[j] <= x1[i])\n", " and not\n", " (x2[i] <= x1[j] and x2[j] <= x1[i])\n", " ;" ] }, { "cell_type": "code", "execution_count": 7, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "HiGHS 1.5.1: \b\b\b\b\b\b\b\b\b\b\b\b\bHiGHS 1.5.1: optimal solution; objective 639.999502\n", "7.40492e+06 simplex iterations\n", "1.05588e+06 branching nodes\n", "absmipgap=0.0608127, relmipgap=9.502e-05\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
wdx1x2y1y2r
0821031.859995e+02267.9995020.0103.00.0
173485.300000e+01101.0000000.073.01.0
2171531.421085e-1453.0000000.0171.01.0
373995.669995e+02639.9995020.099.00.0
4167851.009995e+02185.9995020.0167.01.0
51511723.619995e+02512.9995020.0172.00.0
6541305.129995e+02566.9995020.0130.00.0
7126942.679995e+02361.9995020.0126.01.0
\n", "
" ], "text/plain": [ " w d x1 x2 y1 y2 r\n", "0 82 103 1.859995e+02 267.999502 0.0 103.0 0.0\n", "1 73 48 5.300000e+01 101.000000 0.0 73.0 1.0\n", "2 171 53 1.421085e-14 53.000000 0.0 171.0 1.0\n", "3 73 99 5.669995e+02 639.999502 0.0 99.0 0.0\n", "4 167 85 1.009995e+02 185.999502 0.0 167.0 1.0\n", "5 151 172 3.619995e+02 512.999502 0.0 172.0 0.0\n", "6 54 130 5.129995e+02 566.999502 0.0 130.0 0.0\n", "7 126 94 2.679995e+02 361.999502 0.0 126.0 1.0" ] }, "metadata": {}, "output_type": "display_data" }, { "data": { "image/png": "iVBORw0KGgoAAAANSUhEUgAAA24AAAGJCAYAAADyj2B0AAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjcuMSwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/bCgiHAAAACXBIWXMAAA9hAAAPYQGoP6dpAABelElEQVR4nO3dd3RU1f7+8WfS60wIkAahSgskgIAQpAlIEStc20WKIHxVQKkqVwREKaIIiAp6LWBBr72gKEUIPfSO9CYkBEmZhJA65/cHP0ZHAoQQMkPyfq01a83svc85nxNOysM+xWQYhiEAAAAAgMtyc3YBAAAAAIDLI7gBAAAAgIsjuAEAAACAiyO4AQAAAICLI7gBAAAAgIsjuAEAAACAiyO4AQAAAICLI7gBAAAAgIsjuAEAAACAiyO4AQAKNH78eJlMJv3555/Fts65c+fKZDLpyJEjDu0bNmxQy5Yt5e/vL5PJpK1bt173bRbkwj4XxvX4+gAAcCkENwCAU+Xm5ur+++9XcnKypk+fro8//lhVq1Z1dlmSpDVr1mj8+PFKTU0t9nV/+OGHMplMWr9+vUO7YRiqVauWTCaTNm/e7NCXn5+vypUrq3379sVez+Vs3rxZd999t4KDg+Xn56cGDRrojTfeuOT4iRMnymQyqUGDBgX2Z2dn69lnn1VERIR8fX3VvHlzLV68+HqVDwClAsENAOBUBw8e1NGjRzVy5EgNHDhQjzzyiMqVK1ds6+/Vq5fOnTtXpDC4Zs0avfjii9cluFksFkmS1Wp1aF+0aJEOHDhQYN8PP/ygEydO6Mknnyz2ei5l0aJFio2NVVJSkl544QXNnDlTd955p/74448Cx//xxx+aNGmS/P39L7nOvn376vXXX1fPnj01c+ZMubu764477tCqVauu124AwA3Pw9kFAADKtqSkJElSUFDQdVm/u7u73N3dr8u6r8Wlgtvs2bMVFRWl3bt3F9gXERGhe++9t0RqtFqt6t27t7p166avvvpKbm5X/v/ekSNHqkWLFsrPzy/wNNL169fr888/16uvvqqRI0dKknr37q0GDRromWee0Zo1a4p9PwCgNGDGDQDKqPT0dA0dOlTVqlWTt7e3QkJCdPvtt190el5qaqr69u2roKAgWSwWPfroo8rMzLxofSdOnFC/fv0UGhoqb29v1a9fXx988MFla+jbt6/atm0rSbr//vtlMpnUrl27Asdu375dJpNJP/zwg71t06ZNMplMuvnmmx3Gdu3aVc2bN5d06WvcVq1apWbNmsnHx0c1a9bUO++849A/fvx4jRo1SpJUvXp1mUymAtdT2K/PP10Ibunp6fa248ePa8GCBRo+fLg8PDwc+g4cOKAlS5ZowIAB8vAomf93nT9/vk6dOqWJEyfKzc1NZ8+elc1mu+T4FStW6KuvvtKMGTMuOearr76Su7u7Bg4caG/z8fFR//79tXbtWh0/frw4dwEASg1m3ACgjHr88cf11VdfafDgwYqKitKZM2e0atUq7dmzxyEIPfDAA6pevbomT56szZs367333lNISIheeeUV+5hTp06pRYsWMplMGjx4sCpWrKiFCxeqf//+slqtGjp0aIE1/N///Z8qVaqkSZMm6amnnlKzZs0UGhpa4NgGDRooKChIK1as0N133y1JWrlypdzc3LRt2zZZrVaZzWbZbDatWbPGIRj8044dO9SpUydVrFhR48ePV15ensaNG+ew7e7du2vfvn367LPPNH36dFWoUEGSVLFiRYd1FebrUxCz2SzJccbt3Xffldls1r///W+NGjXKoW/OnDkXBZ6C5ObmKi0t7bJjLggODr7sLNqSJUtkNpt14sQJ3Xvvvdq3b5/8/f3Vq1cvTZ8+XT4+Pvax+fn5GjJkiB577DFFR0dfcp1btmxR7dq17ft/wS233CJJ2rp1qyIjIwtVPwCUKQYAoEyyWCzGoEGDLtk/btw4Q5LRr18/h/b77rvPKF++vENb//79jfDwcOPPP/90aH/ooYcMi8ViZGZmGoZhGB9++KEhyTh8+LB9zLJlywxJxpdffnnFmrt162bccsst9s/du3c3unfvbri7uxsLFy40DMMwNm/ebEgyvv/++0tu89577zV8fHyMo0eP2tt2795tuLu7G3//1fjqq69etGxRvj4FSUxMNCQZL7/8smEYhpGTk2OEhYUZI0aMMAzDMKpUqWJMmTLFMAzDOHfunBEcHGz06NHjiuu98PUszKug/fq7mJgYw8/Pz/Dz8zOGDBlifP3118aQIUMMScZDDz3kMPbNN980LBaLkZSUZBiGYbRt29aoX7/+ReusX7++0b59+4vad+3aZUgy5syZc8V9BICyiBk3ACijgoKCFB8fr5MnTyoiIuKS4x5//HGHz61bt9a3335rn+EyDENff/21HnjgARmG4XBdU+fOnfX5559r8+bNuvXWW6+55tatW2vMmDE6e/as/P39tWrVKk2aNElHjx7VypUr1aVLF61cuVImk0mtWrUqcB35+fn69ddfde+996pKlSr29nr16qlz5876+eefr6qmK319LuWf17h98803OnXqlJ544glJUmBgoL3viy++UHJysgYNGnTFeho2bFjoOzSGhYVdtj8jI0OZmZl6/PHH7XeR7N69u3JycvTOO+9owoQJqlWrls6cOaOxY8fqhRdeuGhG8p/OnTsnb2/vi9ovzN6dO3euULUDQFlDcAOAMmrq1Knq06ePIiMj1aRJE91xxx3q3bu3atSo4TDu7+FGkv2OjykpKTKbzTp9+rRSU1P17rvv6t133y1wWxduQHKtWrdurby8PK1du1aRkZFKSkpS69attWvXLq1cuVLS+dMno6KiFBwcXOA6Tp8+rXPnzqlWrVoX9dWpU+eqg9uVvj6X4uPjIy8vL/t1bLNnz1aXLl1Us2ZNSeeD29/76tWrp9tuu+2K9ZQrV04dO3a8qn24FF9fX0nSww8/7ND+73//W++8847Wrl2rWrVqacyYMQoODtaQIUMKtc7s7OyL2rOyshy2CQBwRHADgDLqgQcesM8OLVq0SK+++qpeeeUVffPNN+ratat93KXuyGgYhiTZb1bxyCOPqE+fPgWOjYmJKZaamzZtKh8fH61YsUJVqlRRSEiIateurdatW+vtt99Wdna2Vq5cqfvuu69YtlcYV/r6XI7ZbJbVatXu3bsVFxenn376yd53YcZt27ZtWrdu3WWfm/Z3OTk5Sk5OLtTYihUrXvaOmxEREdq1a9dF1x2GhIRIOh9O9+/fr3fffVczZszQyZMn7WOysrKUm5urI0eOyGw224N0eHi4Tpw4cdG2EhIS7NsEAFyM4AYAZVh4eLiefPJJPfnkk0pKStLNN9+siRMnOgS3K6lYsaICAwOVn59fbDM9l+Ll5aVbbrlFK1euVJUqVdS6dWtJ52fisrOz9emnn+rUqVNq06bNZev19fXV/v37L+rbu3evw2eTyVS8O/APFotFVqtVs2fPVo0aNdSlSxd734XgNnv2bPn7+18yFP/TmjVrCjUzJ0mHDx9WtWrVLtnfpEkTLV68WCdOnFCdOnXs7RcCWsWKFXXixAnZbDY99dRTeuqppy5aR/Xq1fX000/b7zTZqFEjLVu27KJTSePj4+39AICLEdwAoAzKz89XRkaG/Tor6fwsSkRERIGnsV2Ou7u7evToofnz52vnzp1q0KCBQ//p06eveN3T1WjdurVef/11HTx4UCNGjJAkVahQQfXq1bPfyfFCoLtUvZ07d9Z3332nY8eO2U913LNnj3799VeHsRceIn09HsAtnQ9uCQkJiouL0wsvvOBwh8fAwEDt2bNHixcvVs+ePS972uXfFec1bg888ICmTJmi999/X+3bt7e3v/fee/Lw8FC7du3k5eWlb7/99qJlx4wZo/T0dM2cOdN++qck/etf/9Jrr72md9991/4ct+zsbH344Ydq3rw5d5QEgEsguAFAGZSenq7KlSvrX//6lxo2bKiAgAAtWbJEGzZs0LRp0656fVOmTNGyZcvUvHlzDRgwQFFRUUpOTtbmzZu1ZMmSQp+6VxitW7fWxIkTdfz4cYeA1qZNG73zzjuqVq2aKleufNl1vPjii/rll1/UunVrPfnkk8rLy9OsWbNUv359bd++3T6uSZMmkqTnn39eDz30kDw9PXXXXXfZA921slgsWrZsmXx9fdWvXz+HvsDAQK1fv16S9OSTTxZ6ncV5jVvjxo3Vr18/ffDBB8rLy1Pbtm21fPlyffnllxo9erT9tMaCHgh+YYbtn33NmzfX/fffr9GjRyspKUk33XST5s2bpyNHjuj9998vlroBoDQiuAFAGeTn56cnn3xSixYt0jfffCObzaabbrpJb7/9tv2uhlcjNDRU69ev14QJE/TNN9/o7bffVvny5VW/fv0rPs/sarVs2VLu7u7y8/NTw4YN7e2tW7fWO++8c9nZtgtiYmL066+/avjw4Ro7dqwqV66sF198UQkJCQ7BrVmzZnrppZc0Z84c/fLLL7LZbDp8+HCxBjfp/M0//nkzlcDAQEnn9/fv+1nS5syZoypVqujDDz/Ut99+q6pVq2r69OmXfDZfYXz00Ud64YUX9PHHHyslJUUxMTFasGDBZU9xBYCyzmQU5uppAAAAAIDTuF15CAAAAADAmQhuAAAAAODiCG4AAAAA4OIIbgAAAADg4ghuAAAAAODiCG4AAAAA4OJ4jpskm82mkydPKjAwUCaTydnlAAAAACgjDMNQenq6IiIi5OZ26Xk1gpukkydPKjIy0tllAAAAACijjh8/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", "text/plain": [ "
" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "def pack_boxes_V2(boxes):\n", " W_ub = boxes[\"w\"].sum()\n", "\n", " BOXES = list(boxes.index)\n", " PAIRS = [(i, j) for i in BOXES for j in BOXES if i < j]\n", "\n", " m = AMPL()\n", " m.read(\"pack_boxes_V2.mod\")\n", "\n", " m.set[\"BOXES\"] = BOXES\n", " m.set[\"PAIRS\"] = PAIRS\n", "\n", " m.param[\"w\"] = boxes[\"w\"]\n", " m.param[\"d\"] = boxes[\"d\"]\n", " m.param[\"W_ub\"] = int(W_ub)\n", "\n", " m.solve(solver=SOLVER)\n", " assert m.solve_result == \"solved\", m.solve_result\n", "\n", " soln = boxes.copy()\n", " soln[\"x1\"] = m.var[\"x1\"].to_dict()\n", " soln[\"x2\"] = m.var[\"x2\"].to_dict()\n", " soln[\"y1\"] = m.var[\"y1\"].to_dict()\n", " soln[\"y2\"] = m.var[\"y2\"].to_dict()\n", " soln[\"r\"] = m.var[\"r\"].to_dict()\n", "\n", " return soln\n", "\n", "\n", "soln = pack_boxes_V2(boxes)\n", "display(soln)\n", "show_boxes(soln, D)" ] }, { "cell_type": "markdown", "metadata": { "tags": [] }, "source": [ "## Version 3: Placing and Rotating boxes in two dimensions\n", "\n", "Obviously the packages can be packed closer together by allowing boxes to be stacked deeper into the shelf. New constraints are needed to maintain the bounding boxes within the shelf depth, and to avoid overlaps in the $y$ dimension.\n", "\n", "$$\n", "\\begin{align*}\n", "& \\min W \\\\\n", "\\text{subject to:}\\qquad\\qquad \\\\\n", "x_{i, 2} & \\leq W & \\forall i\\\\\n", "y_{i, 2} & \\leq D & \\forall i\\\\\n", "x_{i, 1}, x_{i, 2} & \\geq 0 & \\forall i \\\\\n", "y_{i, 1}, y_{i, 2} & \\geq 0 & \\forall i \\\\\n", "\\\\\n", "\\begin{bmatrix}\n", "x_{i, 2} \\leq x_{j,1} \\\\\n", "\\end{bmatrix}\n", "\\veebar\n", "\\begin{bmatrix}\n", "x_{j, 2} \\leq x_{i, 1} \\\\\n", "\\end{bmatrix}\n", "& \\veebar \n", "\\begin{bmatrix}\n", "y_{i, 2} \\leq y_{j, 1} \\\\\n", "\\end{bmatrix}\n", "\\veebar\n", "\\begin{bmatrix}\n", "y_{j, 2} \\leq y_{i, 1} \\\\\n", "\\end{bmatrix}\n", "& \\forall i < j \\\\\n", "\\\\\n", "\\begin{bmatrix}\n", "\\neg r_i \\\\\n", "x_{i,2} = x_{i,1} + w_i\\\\\n", "y_{i,2} = y_{i,1} + d_i\\\\\n", "\\end{bmatrix} & \\veebar \n", "\\begin{bmatrix}\n", "r_i \\\\\n", "x_{i,2} = x_{i,1} + d_i\\\\\n", "y_{i,2} = y_{i,1} + w_i\\\\\n", "\\end{bmatrix} & \\forall i < j\n", "\\end{align*}\n", "$$\n" ] }, { "cell_type": "code", "execution_count": 8, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Overwriting pack_boxes_V3.mod\n" ] } ], "source": [ "%%writefile pack_boxes_V3.mod\n", "\n", "set BOXES;\n", "set PAIRS within {BOXES,BOXES};\n", "\n", "param w{BOXES};\n", "param d{BOXES};\n", "param D;\n", "\n", "param W_ub;\n", "\n", "var W >= 0, <= W_ub;\n", "var x1{BOXES} >= 0, <= W_ub;\n", "var x2{BOXES} >= 0, <= W_ub;\n", "var y1{BOXES} >= 0, <= W_ub;\n", "var y2{BOXES} >= 0, <= W_ub;\n", "var r{BOXES} binary;\n", "\n", "minimize minimize_width: W;\n", "\n", "s.t. width {i in BOXES}:\n", " x2[i] <= W;\n", "s.t. height {i in BOXES}:\n", " y2[i] <= D;\n", " \n", "s.t. rotate {i in BOXES}:\n", " r[i] == 0 ==> (x2[i] == x1[i] + w[i] and y2[i] == y1[i] + d[i])\n", " else\n", " (x2[i] == x1[i] + d[i] and y2[i] == y1[i] + w[i]);\n", "\n", "s.t. no_overlap {(i, j) in PAIRS}:\n", " (x2[i] <= x1[j] or x2[j] <= x1[i] or y2[i] <= y1[j] or y2[j] <= y1[i])\n", " and not\n", " (x2[i] <= x1[j] and x2[j] <= x1[i] and y2[i] <= y1[j] and y2[j] <= y1[i])\n", " ;" ] }, { "cell_type": "code", "execution_count": 9, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "HiGHS 1.5.1:HiGHS 1.5.1: optimal solution; objective 265.999999\n", "2.86135e+06 simplex iterations\n", "140133 branching nodes\n", "absmipgap=8.4e-05, relmipgap=3.15789e-07\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
wdx1x2y1y2r
0821030.00000082.000000151.0254.00
17348217.999999265.999999126.0199.01
21715394.999999265.999999205.0258.00
373990.00000099.000000271.0344.01
41678599.000000265.999999258.0343.00
51511720.000000172.0000000.0151.01
65413082.000000212.000000151.0205.01
712694171.999999265.9999990.0126.01
\n", "
" ], "text/plain": [ " w d x1 x2 y1 y2 r\n", "0 82 103 0.000000 82.000000 151.0 254.0 0\n", "1 73 48 217.999999 265.999999 126.0 199.0 1\n", "2 171 53 94.999999 265.999999 205.0 258.0 0\n", "3 73 99 0.000000 99.000000 271.0 344.0 1\n", "4 167 85 99.000000 265.999999 258.0 343.0 0\n", "5 151 172 0.000000 172.000000 0.0 151.0 1\n", "6 54 130 82.000000 212.000000 151.0 205.0 1\n", "7 126 94 171.999999 265.999999 0.0 126.0 1" ] }, "metadata": {}, "output_type": "display_data" }, { "data": { "image/png": "iVBORw0KGgoAAAANSUhEUgAAA24AAAGJCAYAAADyj2B0AAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjcuMSwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/bCgiHAAAACXBIWXMAAA9hAAAPYQGoP6dpAABfXklEQVR4nO3dd3wUdf7H8fembPpuCJAGCU1aIHSEoCACUuSwwKkoCgjiiaBSROVUQFGCeAiICnoWuFP0LNhQUUAIPXRBQJAmiAlBSLIppO78/uDHykqCSQjZJXk9H499PHa+852Zz4TJXd5+Z75jMgzDEAAAAADAbXm4ugAAAAAAwMUR3AAAAADAzRHcAAAAAMDNEdwAAAAAwM0R3AAAAADAzRHcAAAAAMDNEdwAAAAAwM0R3AAAAADAzRHcAAAAAMDNEdwAAEWaMmWKTCaTfv/993Lb54IFC2QymXTkyBGn9s2bN6tTp04KCAiQyWTSjh07Lvsxi3LunEvicvx8AAAoDsENAOBS+fn5uu2223T69GnNmjVL//3vf1WnTh1XlyVJWr9+vaZMmaK0tLRy3/c777wjk8mkTZs2ObUbhqGGDRvKZDJp27ZtTusKCwtVu3ZtdevWrdzrKcrmzZs1evRoNWvWTAEBAYqOjtbtt9+u/fv3F9l/27ZtuummmxQSEiJ/f381b95cL7/88iX3BQBIXq4uAABQtR08eFC//PKL/v3vf+u+++4r9/3fc889GjhwoHx8fEq97fr16/XMM89o6NChCg4OLte6rFarJMlmszm1f/fddzpw4ECR67744gsdP35cs2fPLtdaivPCCy9o3bp1uu2229SiRQslJyfrlVdeUZs2bbRx40Y1b97cqe5+/fqpdevWevrppxUYGKiDBw/q119/vWC/pekLADiL4AYAcKmUlBRJKvdgdI6np6c8PT0vy74vRXHBbd68eYqJidGePXuKXBcZGalbbrmlQmocN26cFi1aJLPZ7Gi74447FBsbq+nTp+vdd9+VdPYcBg8erL59++rjjz+Wh0fxN/SUpi8A4A/8ryUAVFEZGRkaM2aM6tatKx8fH4WGhuqGG2644Pa8tLQ0x4iT1WrVvffeq+zs7Av2d/z4cQ0bNkxhYWHy8fFRs2bN9Pbbb1+0hqFDh+q6666TJN12220ymUzq2rVrkX137twpk8mkL774wtG2detWmUwmtWnTxqlvnz591KFDB0nFP+O2du1atW/fXr6+vmrQoIFef/11p/VTpkzRhAkTJEn16tWTyWQqcj8l/fn82bnglpGR4Wg7duyYlixZonHjxsnLy8tp3YEDB7R8+XKNGDFCXl4V899dO3Xq5BTaJKlhw4Zq1qyZ9u7d62hbtGiRTpw4oeeff14eHh7KysqS3W4vcp+l6QsA+AMjbgBQRT3wwAP6+OOPNXr0aMXExOjUqVNau3at9u7d6xSEbr/9dtWrV0/x8fHatm2b3nzzTYWGhuqFF15w9Dlx4oQ6duwok8mk0aNHq2bNmvrmm280fPhw2Ww2jRkzpsga/vGPf6hWrVqaNm2aHn74YbVv315hYWFF9m3evLmCg4O1evVq3XTTTZKkNWvWyMPDQz/88INsNpssFovsdrvWr1+v+++/v9hz37Vrl3r27KmaNWtqypQpKigo0OTJk52O3b9/f+3fv1/vv/++Zs2apRo1akiSatas6bSvkvx8imKxWCQ5j7i98cYbslgsuuuuuzRhwgSndfPnz5enp+dFz0s6+8xgenr6RfucExISUuoRL8MwdOLECTVr1szRtnz5clksFh0/fly33HKL9u/fr4CAAN1zzz2aNWuWfH19y9QXAHAeAwBQJVmtVmPUqFHFrp88ebIhyRg2bJhT+6233mpUr17dqW348OFGRESE8fvvvzu1Dxw40LBarUZ2drZhGIbxzjvvGJKMw4cPO/qsXLnSkGR89NFHf1lz3759jauvvtqx3L9/f6N///6Gp6en8c033xiGYRjbtm0zJBmff/55sce85ZZbDF9fX+OXX35xtO3Zs8fw9PQ0zv+/xhdffPGCbcvy8ylKcnKyIcl47rnnDMMwjLy8PCM8PNwYP368YRiGER0dbUyfPt0wDMM4c+aMERISYgwYMOAv93vu51mST1Hn9Vf++9//GpKMt956y9HWokULw9/f3/D39zceeugh45NPPjEeeughQ5IxcOBAp+1L0xcA8AdG3ACgigoODlZiYqJ+++03RUZGFtvvgQcecFru3LmzPv30U8cIl2EY+uSTT3T77bfLMAyn6fF79eqlDz74QNu2bdM111xzyTV37txZTz31lLKyshQQEKC1a9dq2rRp+uWXX7RmzRr17t1ba9askclk0rXXXlvkPgoLC/Xtt9/qlltuUXR0tKO9adOm6tWrl77++utS1fRXP5/i/PkZt8WLF+vEiRMaOXKkJCkoKMix7sMPP9Tp06c1atSov6ynZcuWWrZsWYlqDw8PL1G/c3766SeNGjVKcXFxGjJkiKM9MzNT2dnZeuCBBxwzQ/bv3195eXl6/fXX9eyzz6phw4al7gsA+APBDQCqqBkzZmjIkCGKiopS27ZtdeONN2rw4MGqX7++U7/zw40kVatWTZKUmpoqi8WikydPKi0tTW+88YbeeOONIo91bgKSS9W5c2cVFBRow4YNioqKUkpKijp37qzdu3drzZo1ks7ePhkTE6OQkJAi93Hy5EmdOXOmyHDQuHHjUge3v/r5FMfX11dms9nxHNu8efPUu3dvNWjQQNLZ4Hb+uqZNm+r666//y3qqVaumHj16lOocSiI5OVl9+/aV1WrVxx9/7DThi5+fnyTpzjvvdNrmrrvu0uuvv64NGzY4ft6l6QsA+APBDQCqqNtvv90xOvTdd9/pxRdf1AsvvKDFixerT58+jn7FzchoGIYkOSaWuPvuu51GYc7XokWLcqm5Xbt28vX11erVqxUdHa3Q0FA1atRInTt31muvvabc3FytWbNGt956a7kcryT+6udzMRaLRTabTXv27FFCQoK++uorx7pzI24//PCDNm7cWOJ3nOXl5en06dMl6luzZs0SzbiZnp6uPn36KC0tTWvWrLlghDYyMlK7d+++4PnE0NBQSWdDbFn6AgD+QHADgCosIiJCDz74oB588EGlpKSoTZs2ev75552C21+pWbOmgoKCVFhYeFlGes5nNpt19dVXa82aNYqOjlbnzp0lnR2Jy83N1XvvvacTJ06oS5cuF63Xz89PP//88wXr9u3b57RsMpnK9wT+xGq1ymazad68eapfv7569+7tWHcuuM2bN08BAQHFhuI/W79+fYlG5iTp8OHDqlu37kX75OTkqF+/ftq/f7+WL1+umJiYC/q0bdtWy5Yt0/Hjx9W4cWNH+2+//SbJeUKX0vQFAPyB4AYAVVBhYaEyMzMdz1lJZ0c8IiMjlZubW6p9eXp6asCAAVq0aJF+/PFHp5cyS2dvTSzPP8Y7d+6sl156SQcPHtT48eMlSTVq1FDTpk0dMzmeC3TF1durVy999tlnOnr0qONWx7179+rbb7916hsQECDp7JT/l4PValVSUpISEhL09NNPO83wGBQUpL1792rZsmUaNGjQRW+7PF95PuNWWFioO+64Qxs2bNDnn3+uuLi4Ivvdfvvtmj59ut566y1169bN0f7mm2/Ky8vL6RUPpekLAPgDwQ0AqqCMjAzVrl1bf//739WyZUsFBgZq+fLl2rx5s2bOnFnq/U2fPl0rV65Uhw4dNGLECMXExOj06dPatm2bli9fXuJb90qic+fOev7553Xs2DGngNalSxe9/vrrqlu3rmrXrn3RfTzzzDNaunSpOnfurAcffFAFBQWaO3eumjVrpp07dzr6tW3bVpL05JNPauDAgfL29la/fv0cge5SWa1WrVy5Un5+fho2bJjTuqCgIG3atEmS9OCDD5Z4n+X5jNv48eP1xRdfqF+/fjp9+rTjhdvn3H333ZKk1q1ba9iwYXr77bdVUFCg6667TqtWrdJHH32kiRMnOt1aWZq+AIA/ENwAoAry9/fXgw8+qO+++06LFy+W3W7XVVddpddee80xq2FphIWFadOmTXr22We1ePFivfbaa6pevbqaNWv2l+8zK61OnTrJ09NT/v7+atmypaO9c+fOev311y862nZOixYt9O2332rcuHGaNGmSateurWeeeUZJSUlOwa19+/aaOnWq5s+fr6VLl8put+vw4cPlGtyksxN1/HkylaCgIElnz/f886xIO3bskCR9+eWX+vLLLy9Yfy64SWffMxcdHa133nlHn376qerUqaNZs2YV+Q6/0vQFAJxlMkry9DQAAAAAwGU8/roLAAAAAMCVCG4AAAAA4OYIbgAAAADg5ghuAAAAAODmCG4AAAAA4OYIbgAAAADg5niPmyS73a7ffvtNQUFBMplMri4HAAAAQBVhGIYyMjIUGRkpD4/ix9UIbpJ+++03RUVFuboMAAAAAFXUsWPHVLt27WLXE9wkBQUFSTr7w7JYLC6uBrgy2HJtinopSsfGHZPF5yK/NzabFBUlHTsm8fsFAADgxGazKSoqypFJikNwkxy3R1osFoIbUFK5knz///fmYsHtHIuF4AYAAFCMv3pki8lJAAAAAMDNEdwAAAAAwM0R3AAAAADAzfGMGwAAAColwzBUUFCgwsJCV5eCKszT01NeXl6X/NoxghsAAAAqnby8PCUlJSk7O9vVpQDy9/dXRESEzGZzmfdBcAMAAEClYrfbdfjwYXl6eioyMlJms/mSRzuAsjAMQ3l5eTp58qQO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", "text/plain": [ "
" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "def pack_boxes_V3(boxes, D):\n", " W_ub = boxes[\"w\"].sum()\n", "\n", " BOXES = list(boxes.index)\n", " PAIRS = [(i, j) for i in BOXES for j in BOXES if i < j]\n", "\n", " m = AMPL()\n", " m.read(\"pack_boxes_V3.mod\")\n", "\n", " m.set[\"BOXES\"] = BOXES\n", " m.set[\"PAIRS\"] = PAIRS\n", "\n", " m.param[\"w\"] = boxes[\"w\"]\n", " m.param[\"d\"] = boxes[\"d\"]\n", " m.param[\"W_ub\"] = int(W_ub)\n", " m.param[\"D\"] = int(D)\n", "\n", " m.solve(solver=SOLVER)\n", " assert m.solve_result == \"solved\", m.solve_result\n", "\n", " r = m.var[\"r\"].to_dict()\n", " r = {i: int(round(r[i])) for i in r}\n", "\n", " soln = boxes.copy()\n", " soln[\"x1\"] = m.var[\"x1\"].to_dict()\n", " soln[\"x2\"] = m.var[\"x2\"].to_dict()\n", " soln[\"y1\"] = m.var[\"y1\"].to_dict()\n", " soln[\"y2\"] = m.var[\"y2\"].to_dict()\n", " soln[\"r\"] = r\n", " return soln\n", "\n", "\n", "soln = pack_boxes_V3(boxes, D)\n", "display(soln)\n", "show_boxes(soln, D)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Advanced Topic: Symmetry Breaking\n", "\n", "One of the issues in combinatorial problem is the challenge of symmetries. A symmetry is a situation where a change in solution configuration leaves the objective unchanged. Strip packing problems are especially susceptible to symmetries.\n", "\n", "Symmetries can significantly increase the effort needed to find and and verify an optimal solution. Trespalacios and Grossmann recently presented modification to the strip packing problem to reduce the number of symmetries. This is described in the following paper and implemented in the accompanying AMPL model.\n", "\n", "Trespalacios, F., & Grossmann, I. E. (2017). Symmetry breaking for generalized disjunctive programming formulation of the strip packing problem. Annals of Operations Research, 258(2), 747-759.\n" ] }, { "cell_type": "code", "execution_count": 10, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Overwriting pack_boxes_V4.mod\n" ] } ], "source": [ "%%writefile pack_boxes_V4.mod\n", "\n", "set BOXES;\n", "set PAIRS within {BOXES,BOXES};\n", "\n", "param w{BOXES};\n", "param d{BOXES};\n", "param D;\n", "\n", "param W_ub;\n", "\n", "var W >= 0, <= W_ub;\n", "var x1{BOXES} >= 0, <= W_ub;\n", "var x2{BOXES} >= 0, <= W_ub;\n", "var y1{BOXES} >= 0, <= W_ub;\n", "var y2{BOXES} >= 0, <= W_ub;\n", "var r{BOXES} binary;\n", "\n", "minimize minimize_width: W;\n", "\n", "s.t. width {i in BOXES}:\n", " x2[i] <= W;\n", "s.t. height {i in BOXES}:\n", " y2[i] <= D;\n", " \n", "s.t. rotate {i in BOXES}:\n", " r[i] == 0 ==> (x2[i] == x1[i] + w[i] and y2[i] == y1[i] + d[i])\n", " else\n", " (x2[i] == x1[i] + d[i] and y2[i] == y1[i] + w[i])\n", " ;\n", "\n", "s.t. no_overlap {(i, j) in PAIRS}:\n", " x2[i] <= x1[j] or\n", " x2[j] <= x1[i] or\n", " (y2[i] <= y1[j] and x2[i] >= x1[j] + 1 and x2[j] >= x1[i] + 1) or\n", " (y2[j] <= y1[i] and x2[i] >= x1[j] + 1 and x2[j] >= x1[i] + 1);" ] }, { "cell_type": "code", "execution_count": 11, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "HiGHS 1.5.1: \b\b\b\b\b\b\b\b\b\b\b\b\bHiGHS 1.5.1: optimal solution; objective 266\n", "1.4118e+06 simplex iterations\n", "74606 branching nodes\n", "absmipgap=0.00274, relmipgap=1.03008e-05\n" ] }, { "data": { "text/html": [ "
\n", "\n", "\n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", " \n", "
wdx1x2y1y2r
082103178.0260.00.0103.00
173480.048.053.0126.01
2171530.0171.00.053.00
37399167.0266.0258.0331.01
4167850.0167.0258.0343.00
515117294.0266.0107.0258.01
65413048.0178.053.0107.01
7126940.094.0126.0252.01
\n", "
" ], "text/plain": [ " w d x1 x2 y1 y2 r\n", "0 82 103 178.0 260.0 0.0 103.0 0\n", "1 73 48 0.0 48.0 53.0 126.0 1\n", "2 171 53 0.0 171.0 0.0 53.0 0\n", "3 73 99 167.0 266.0 258.0 331.0 1\n", "4 167 85 0.0 167.0 258.0 343.0 0\n", "5 151 172 94.0 266.0 107.0 258.0 1\n", "6 54 130 48.0 178.0 53.0 107.0 1\n", "7 126 94 0.0 94.0 126.0 252.0 1" ] }, "metadata": {}, "output_type": "display_data" }, { "data": { "image/png": "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XpJUu3ZtrV27Vq+++qpuuukmh22ZzWYFBgbK3d1d4eHhRdaUmZmpN998U++99546deok6VyIql69ur3Ppew3KipKM2bMkMlkUv369bVr1y7NmDFDQ4cOlZeXl/z8/Iqs5WLHXZStW7eqfv36DvnhPC8vL3l6luzfxFU4Nbj16tXL4fMLL7ygefPmaePGjfbgVtw/nCR9//332rt3r5YvX66wsDA1bdpUkyZN0pNPPqnx48fLy8vrih8DAAAArg4B3h7aNb6rU/ZbUk2aNFGnTp0UGxurbt26qWvXrvrnP/+pSpUq2fvExcU5rBMREaHU1FRJ0sGDB5WdnV0ozOTl5alZs2alqv/QoUPKy8tT69at7W0hISGqX7++/fOl7LdNmzYymUz2z/Hx8Zo+fbqsVutF67jYcRdl69atatGiRZHL9u/frwYNGlx0f67GZe48tFqtWrx4sbKysuwpXZLef/99vffeewoPD1evXr307LPP2lPzhg0bFBsbq7CwMHv/bt26adiwYdqzZ0+xJ2dubq5yc3Ptny0WyxU6KgAAALgKk8lU4pEvZ3F3d9eyZcu0fv16ff/995ozZ46efvppJSUlqVatWpJUaKTIZDLJZrNJOjc6JklfffWVqlWr5tDP29v7itVdHvu92HEXZevWrYUGiqRz9+t98cUXGj16dJnUVV6cHtx27dql+Ph45eTkKCAgQJ9++qliYmIkSffcc49q1KihyMhI7dy5U08++aT279+vJUuWSJJSUlIcQpsk++eUlJRi95mQkKAJEyZcoSMCAAAASs9kMumGG27QDTfcoOeee041atTQp59+WqKgERMTI29vbx09erTQZZGlVadOHXl6eiopKUnR0dGSpDNnzujAgQP2fVzKfpOSkhw+b9y4UXXr1pW7u7u8vLz+duStJA4fPqy0tDQ1b97cod1qterBBx+Ur6+vhg8fftn7KU9OD27169fX9u3blZ6ero8//lgDBw5UYmKiYmJi9MADD9j7xcbGKiIiQp06ddKhQ4dUp06dUu9z7NixDie+xWJxuPERAAAAcIakpCStWLFCXbt2VWhoqJKSknTy5Ek1bNiwROsHBgbq8ccf16hRo2Sz2XTjjTcqPT1d69atU1BQkAYOHHjJNQUEBGjIkCEaM2aMKleurNDQUD399NNyc/tznsNL2e/Ro0c1evRo/fvf/9bW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", "text/plain": [ "
" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "def pack_boxes_V4(boxes, D):\n", " W_ub = boxes[\"w\"].sum()\n", "\n", " BOXES = list(boxes.index)\n", " PAIRS = [(i, j) for i in BOXES for j in BOXES if i < j]\n", "\n", " m = AMPL()\n", " m.read(\"pack_boxes_V4.mod\")\n", "\n", " m.set[\"BOXES\"] = BOXES\n", " m.set[\"PAIRS\"] = PAIRS\n", "\n", " m.param[\"w\"] = boxes[\"w\"]\n", " m.param[\"d\"] = boxes[\"d\"]\n", " m.param[\"W_ub\"] = int(W_ub)\n", " m.param[\"D\"] = int(D)\n", "\n", " m.solve(solver=SOLVER)\n", " assert m.solve_result == \"solved\", m.solve_result\n", "\n", " r = m.var[\"r\"].to_dict()\n", " r = {i: int(round(r[i])) for i in r}\n", "\n", " soln = boxes.copy()\n", " soln[\"x1\"] = m.var[\"x1\"].to_dict()\n", " soln[\"x2\"] = m.var[\"x2\"].to_dict()\n", " soln[\"y1\"] = m.var[\"y1\"].to_dict()\n", " soln[\"y2\"] = m.var[\"y2\"].to_dict()\n", " soln[\"r\"] = r\n", "\n", " return soln\n", "\n", "\n", "soln = pack_boxes_V4(boxes, D)\n", "display(soln)\n", "show_boxes(soln, D)" ] } ], "metadata": { "kernelspec": { "display_name": "Python 3 (ipykernel)", "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.10.6" } }, "nbformat": 4, "nbformat_minor": 4 }