EURO 2025, Leeds
System prompt to give context and define reponse structure:
I want you to act as an expert in Operations Research, helping
users identify and describe their optimization problem clearly.
I likely have an optimization problem on my hands but, I need help
with identifying and formulating it.
Your response will be depending on whether we are in Step 1 or 2.
If we are in Step 1, we should have a discussion to make sure we
both understand the context, variables and constraints.
You need to ask me questions so that we can together identify a
proper optimization problem and its components.
This discussion will continue until we have a good understanding of
the problem. After we have that, we move on to Step 2.
Formulate the problem in a structured manner. In the end, the
problem description will be given for review to upper management.
This means that the context needs to be stated explicitly, and the
constraints are stated explicitly rather than implicitly. Your
response should ONLY follow the following template:
## 📝 Problem description
Context: what is the problem on a high level, what industry and
role are we in, etc.
Objective:
objective description
Constraints:
constraints in an itemized list
Data:
necessary data in an itemized list, if applicable, specify which
columns are expected
## ⏯️ Next steps
Now that you have a problem description:
1. review the details and, if necessary, either discuss here or
adjust manually.
2. prepare your data files (real or dummy data).
3. copy-paste the Problem Description and paste it together with
the data files into [Gurobi AI Modeling Assistant]
(https://chatgpt.com/g/g-g69cy3XAp-gurobi-ai-modeling-assistant).
System prompt:
I want you to act as an expert in optimization and Python
programming, specifically using gurobipy.
I will write you a problem description and you guide me to convert
this problem into an optimization model, solve it and explain the
results.
Your response will follow the template:
Install gurobipy using Code Interpreter:
`!pip install /mnt/data/gurobipy-12.0.1-cp311-cp311-manylinux2014_
x86_64.manylinux_2_17_x86_64.whl`
If the user provides any data files, read them and make sure you
understand the complete context before moving on.
## 🔢 Problem definition
Convert the problem description into a mathematical model. Use
proper mathematical notations
## 🐍 Build and solve model
Create and solve the model using Code Interpreter. ANY TIME YOU
WRITE CODE YOU DO THIS IN A Code Interpreter & Data Analysis BLOCK
THAT YOU EXECUTE, YOU NEVER WRITE CODE AS TEXT.
Model non-divisible items as integer variables.
## 👩🏫 Results
Display solution, objective values and decision variables. Note any
unaddressed aspects.
List the gurobipy version used (infer from wheel gurobipy wheel name)
Close with the following sentence: "For more guidance, see the
[documentation](https://gurobi-ai-modeling.readthedocs.io/) for this
Custom GPT"
Prompt
Assume there is a large rectangle.
I need to pack a given set of smaller rectangles into the large one.
Write a linear mathematical problem formulation for this feasibility problem.
Response
Here’s a comprehensive linear mathematical formulation for the 2D rectangle packing feasibility problem:
We have a large rectangle (container) with dimensions \(W \times H\) and a set of smaller rectangles that need to be packed into it without overlapping. This is a feasibility problem to determine if all rectangles can fit.
Since this is a feasibility problem, we can use a dummy objective: \[\text{minimize } \quad 0\]
1. Container Bounds: For each rectangle \(i \in I\): \[x_i + w_i (1 - r_i) + h_i r_i \leq W\] \[y_i + h_i (1 - r_i) + w_i r_i \leq H\]
2. Non-overlapping Constraints: For each pair of rectangles \(i, j \in I\) where \(i < j\):
\[x_i + w_i (1 - r_i) + h_i r_i \leq x_j + M(1 - \alpha_{ij})\] \[x_j + w_j (1 - r_j) + h_j r_j \leq x_i + M(1 - \beta_{ij})\] \[y_i + h_i (1 - r_i) + w_i r_i \leq y_j + M(1 - \gamma_{ij})\] \[y_j + h_j (1 - r_j) + w_j r_j \leq y_i + M(1 - \delta_{ij})\]
3. Logical Constraints: For each pair \(i, j \in I\) where \(i < j\): \[\alpha_{ij} + \beta_{ij} + \gamma_{ij} + \delta_{ij} \geq 1\]
4. Variable Domains: \[x_i, y_i \geq 0 \quad \forall i \in I\] \[r_i, \alpha_{ij}, \beta_{ij}, \gamma_{ij}, \delta_{ij} \in \{0, 1\} \quad \forall i, j \in I, i < j\]
If rotation is not allowed, the formulation simplifies by removing \(r_i\) variables:
Container Bounds: \[x_i + w_i \leq W \quad \forall i \in I\] \[y_i + h_i \leq H \quad \forall i \in I\]
Non-overlapping Constraints: \[x_i + w_i \leq x_j + M(1 - \alpha_{ij}) \quad \forall i, j \in I, i < j\] \[x_j + w_j \leq x_i + M(1 - \beta_{ij}) \quad \forall i, j \in I, i < j\] \[y_i + h_i \leq y_j + M(1 - \gamma_{ij}) \quad \forall i, j \in I, i < j\] \[y_j + h_j \leq y_i + M(1 - \delta_{ij}) \quad \forall i, j \in I, i < j\]
This formulation creates a mixed-integer linear programming (MILP) problem that can be solved efficiently with Gurobi.
References:
Prompt
Provide Python code based on gurobipy for the problem without rotation.
Response
Here’s a comprehensive Python implementation using gurobipy for the 2D rectangle packing problem without rotation:
# Position variables (bottom-left corner coordinates)
self.x_vars = self.model.addVars(n, vtype=GRB.CONTINUOUS, lb=0, name="x")
self.y_vars = self.model.addVars(n, vtype=GRB.CONTINUOUS, lb=0, name="y")
# Binary variables for non-overlapping constraints
self.alpha_vars = self.model.addVars(n, n, vtype=GRB.BINARY, name="alpha")
self.beta_vars = self.model.addVars(n, n, vtype=GRB.BINARY, name="beta")
self.gamma_vars = self.model.addVars(n, n, vtype=GRB.BINARY, name="gamma")
self.delta_vars = self.model.addVars(n, n, vtype=GRB.BINARY, name="delta")
# For each pair of rectangles (i,j), exactly one spatial relationship must hold
for i in range(n):
for j in range(i + 1, n):
w_i, h_i = self.rectangles[i]
w_j, h_j = self.rectangles[j]
# Four possible relative positions using big-M
self.model.addConstr(
self.x_vars[i] + w_i <= self.x_vars[j] + M * (1 - self.alpha_vars[i, j])
)
# ... (similar for other three directions)
# Logical constraint: at least one position must be enforced
self.model.addConstr(
self.alpha_vars[i, j] + self.beta_vars[i, j] +
self.gamma_vars[i, j] + self.delta_vars[i, j] >= 1
)
The implementation successfully:
The model generates approximately O(n²) binary variables and constraints for n rectangles, making it suitable for small to medium-sized instances (typically up to 20-50 rectangles depending on computational resources).
Attachments:
Prompt
Show a single-commodity flow formulation for the capacitated vehicle routing problem.
Response
I’ll present the single-commodity flow formulation for the Capacitated Vehicle Routing Problem (CVRP). This formulation treats the problem as a network flow problem where a single commodity (representing vehicle capacity) flows through the network.
The CVRP involves finding optimal routes for a fleet of identical vehicles with limited capacity \(Q\) to serve a set of customers with known demands, starting and ending at a central depot, while minimizing total travel cost.
\[\min \sum_{(i,j) \in A} c_{ij} x_{ij}\]
1. Flow Conservation at Depot: \[\sum_{j \in V \setminus \{0\}} f_{0j} = \sum_{i=1}^{n} d_i\] \[\sum_{i \in V \setminus \{0\}} f_{i0} = 0\]
2. Flow Conservation at Customer Nodes: \[\sum_{j \in V \setminus \{i\}} f_{ij} - \sum_{j \in V \setminus \{i\}} f_{ji} = d_i \quad \forall i \in \{1, \ldots, n\}\]
3. Vehicle Flow Constraints: \[\sum_{j \in V \setminus \{0\}} x_{0j} \leq K\] \[\sum_{i \in V \setminus \{0\}} x_{i0} = \sum_{j \in V \setminus \{0\}} x_{0j}\]
4. Customer Visit Constraints: \[\sum_{i \in V \setminus \{j\}} x_{ij} = 1 \quad \forall j \in \{1, \ldots, n\}\] \[\sum_{j \in V \setminus \{i\}} x_{ij} = 1 \quad \forall i \in \{1, \ldots, n\}\]
5. Flow-Arc Relationship: \[f_{ij} \leq Q \cdot x_{ij} \quad \forall (i,j) \in A\]
6. Capacity Constraints: \[f_{ij} \leq Q \quad \forall (i,j) \in A\]
7. Non-negativity and Binary Constraints: \[x_{ij} \in \{0,1\} \quad \forall (i,j) \in A\] \[f_{ij} \geq 0 \quad \forall (i,j) \in A\]
Advantages:
Limitations:
Learn more:
Prompt
Show a single-commodity flow formulation for the capacitated vehicle routing problem.
Response
I’ll present a comprehensive single-commodity flow formulation for the Capacitated Vehicle Routing Problem (CVRP). This formulation treats the problem as a network flow problem where each vehicle route corresponds to a flow of a single commodity.
The CVRP involves finding optimal routes for a fleet of vehicles with limited capacity to serve a set of customers from a central depot, minimizing total travel cost while ensuring all customers are visited exactly once.
\[\min \sum_{k=1}^{K} \sum_{(i,j) \in A} c_{ij} x_{ij}^k\]
1. Customer Visit Constraints: Each customer must be visited exactly once by exactly one vehicle: \[\sum_{k=1}^{K} \sum_{j \in V} x_{ij}^k = 1 \quad \forall i \in V \setminus \{0\}\]
2. Flow Conservation at Customers: For each customer, inflow equals outflow for each vehicle: \[\sum_{j \in V} x_{ji}^k = \sum_{j \in V} x_{ij}^k \quad \forall i \in V, \forall k \in K\]
3. Depot Constraints: Each vehicle can leave and return to the depot at most once: \[\sum_{j \in V \setminus \{0\}} x_{0j}^k \leq 1 \quad \forall k \in K\] \[\sum_{i \in V \setminus \{0\}} x_{i0}^k \leq 1 \quad \forall k \in K\]
4. Commodity Flow Conservation: At each customer node, the flow decreases by the customer’s demand: \[\sum_{j \in V} f_{ji}^k - \sum_{j \in V} f_{ij}^k = d_i \sum_{j \in V} x_{ji}^k \quad \forall i \in V \setminus \{0\}, \forall k \in K\]
At the depot, the outgoing flow equals the total demand served by each vehicle: \[\sum_{j \in V \setminus \{0\}} f_{0j}^k - \sum_{i \in V \setminus \{0\}} f_{i0}^k = -\sum_{i \in V \setminus \{0\}} d_i \sum_{j \in V} x_{ij}^k \quad \forall k \in K\]
5. Flow-Arc Relationship: Flow can only exist on arcs that are traversed: \[f_{ij}^k \leq Q \cdot x_{ij}^k \quad \forall (i,j) \in A, \forall k \in K\]
6. Capacity Constraints: The flow on any arc cannot exceed vehicle capacity: \[f_{ij}^k \leq Q \quad \forall (i,j) \in A, \forall k \in K\]
7. Non-negativity and Binary Constraints: \[x_{ij}^k \in \{0,1\} \quad \forall (i,j) \in A, \forall k \in K\] \[f_{ij}^k \geq 0 \quad \forall (i,j) \in A, \forall k \in K\]
This formulation is particularly effective for medium-sized instances and provides a strong linear programming relaxation compared to other CVRP formulations.
Learn more:
Prompt
Do we need the vehicle index k?
Response
Excellent question! You’re absolutely right to question this. In a true single-commodity flow formulation, we typically do not need the vehicle index \(k\). The formulation I provided was actually a vehicle-indexed formulation. Let me present the cleaner single-commodity flow formulation without the vehicle index:
\[\min \sum_{(i,j) \in A} c_{ij} x_{ij}\]
1. Customer Visit Constraints: Each customer must be visited exactly once: \[\sum_{j \in V} x_{ij} = 1 \quad \forall i \in V \setminus \{0\}\]
2. Flow Conservation: \[\sum_{j \in V} x_{ji} = \sum_{j \in V} x_{ij} \quad \forall i \in V\]
3. Commodity Flow Conservation: At each customer, flow decreases by the customer’s demand: \[\sum_{j \in V} f_{ji} - \sum_{j \in V} f_{ij} = -d_i \quad \forall i \in V \setminus \{0\}\]
At the depot, net outflow equals total demand: \[\sum_{j \in V \setminus \{0\}} f_{0j} - \sum_{i \in V \setminus \{0\}} f_{i0} = \sum_{i=1}^{n} d_i\]
4. Flow-Arc Relationship: \[f_{ij} \leq Q \cdot x_{ij} \quad \forall (i,j) \in A\]
5. Vehicle Count Constraint: \[\sum_{j \in V \setminus \{0\}} x_{0j} \leq K\]
6. Integrality (for exact solution): \[x_{ij} \in \mathbb{Z}_+ \quad \forall (i,j) \in A\]
The vehicle assignment can be recovered from the solution during post-processing if needed, but the optimization doesn’t require explicit vehicle indexing.
Prompt
Create Python code for this formulation based on gurobipy. Generate a small test instance with 3 vehicles and 5 customers.
Response
Perfect! The model is now working correctly. Here’s the complete Python implementation of the single-commodity flow formulation for CVRP using gurobipy:
The code successfully demonstrates several important aspects:
dict()
constructor to avoid potential issuesaddVars()
for efficient variable creationquicksum()
for constraint buildingThe code implements the key constraints:
The optimal solution found:
The flow variables show how the load decreases along the route:
This demonstrates the power of the single-commodity flow formulation in naturally handling capacity constraints and subtour elimination through flow conservation.
Would you like me to explain any specific part of the formulation in more detail, or would you like to see how to extend this model to handle additional constraints like time windows or multiple depots?
Attachments:
©️ Gurobi Optimization
gurobi.github.io/slides/