In [1] a question was posed about designing a sports schedule.
We have the following information:
- There are 24 teams
- There are 23 rounds
- In every round, each team plays against another team. A team plays exactly once in a round. I.e., there are 12 games per round.
- A team \(t1\) plays against team \(t2\) exactly once.
This is actually not too difficult to model.
Math Programming Model
We define as binary decision variable: \[\mathit{game}_{t1,t2,r} = \begin{cases} 1 & \text{if team \(t1\) plays against team \(t2\) in round \(r\)}\\ 0 & \text{otherwise} \end{cases}\] To prevent double counting, we use the convention that \(\mathit{game}_{t1,t2,r}\) is only defined when \(t1 \lt t2\). So, we have in the model \(\mathit{game}_{team2,team8,round4}\), but we will never use: \(\mathit{game}_{team8,team2,round4}\). This is a little bit of a complicating factor in the model, but the pay-off is that the bookkeeping becomes in the end simpler.
With this we can formulate:
| Mixed-Integer Programming Model |
|---|
| \[\begin{align}\min\>& 0 && &&\text{dummy objective} \\ & \sum_{t2|t1\lt t2} \color{darkred}{\mathit{game}}_{t1,t2,r} + \sum_{t2|t2\lt t1} \color{darkred}{\mathit{game}}_{t2,t1,r} = 1 && \forall t1,r &&\text{play exactly one opponent each round}\\ & \sum_r \color{darkred}{\mathit{game}}_{t1,t2,r}=1&&\forall t1,t2|t1 \lt t2 && \text{meet opponent exactly once}\\ &\color{darkred}{\mathit{game}}_{t1,t2,r} \in \{0,1\} &&\forall t1,t2,r|t1 \lt t2 &&\text{binary variables} \end{align}\] |
The model does not have a real objective: we are just looking for a feasible solution. The first constraint is the most complicated one. Basically it says \[\sum_{t2} {\mathit{game}}_{t1,t2,r} = 1 \>\> \forall t1,r\] but as we only use \({\mathit{game}}_{t1,t2,r}\) for \(t1 \lt t2\), we need to split things in two. This can be visualized as follows:
| Opponents of team t3 |
This is a rather simple model. But it will deliver the schedules we are looking for:
---- 24 VARIABLE game.L schedule for teams
round1 round2 round3 round4 round5 round6 round7 round8
team1 .team15 1
team1 .team16 1
team1 .team17 1
team1 .team18 1
team1 .team19 1
team1 .team20 1
team1 .team22 1
team1 .team24 1
team2 .team12 1
team2 .team15 1
team2 .team16 1
team2 .team19 1
team2 .team20 1
team2 .team21 1
team2 .team23 1
team2 .team24 1
team3 .team12 1
team3 .team13 1
team3 .team14 1
team3 .team15 1
team3 .team16 1
team3 .team21 1
team3 .team23 1
team3 .team24 1
team4 .team10 1
team4 .team14 1
team4 .team15 1
team4 .team16 1
team4 .team18 1
team4 .team21 1
team4 .team22 1
team4 .team23 1
team5 .team11 1
team5 .team15 1
team5 .team16 1
team5 .team18 1
team5 .team19 1
team5 .team20 1
team5 .team21 1
team5 .team22 1
team6 .team9 1
team6 .team10 1
team6 .team11 1
team6 .team16 1
team6 .team17 1
team6 .team20 1
team6 .team22 1
team6 .team23 1
team7 .team9 1
team7 .team10 1
team7 .team12 1
team7 .team14 1
team7 .team16 1
team7 .team19 1
team7 .team21 1
team7 .team24 1
team8 .team9 1
team8 .team11 1
team8 .team12 1
team8 .team13 1
team8 .team14 1
team8 .team16 1
team8 .team19 1
team8 .team22 1
team9 .team18 1
team9 .team20 1
team9 .team21 1
team9 .team22 1
team9 .team23 1
team10.team17 1
team10.team20 1
team10.team21 1
team10.team23 1
team10.team24 1
team11.team17 1
team11.team18 1
team11.team19 1
team11.team23 1
team11.team24 1
team12.team17 1
team12.team18 1
team12.team22 1
team12.team24 1
team13.team17 1
team13.team18 1
team13.team19 1
team13.team20 1
team13.team23 1
team13.team24 1
team14.team17 1
team14.team18 1
team14.team20 1
team14.team21 1
team15.team17 1
team15.team19 1
team15.team22 1
+ round9 round10 round11 round12 round13 round14 round15 round16
team1 .team9 1
team1 .team10 1
team1 .team11 1
team1 .team12 1
team1 .team13 1
team1 .team14 1
team1 .team21 1
team1 .team23 1
team2 .team9 1
team2 .team10 1
team2 .team11 1
team2 .team13 1
team2 .team14 1
team2 .team17 1
team2 .team18 1
team2 .team22 1
team3 .team9 1
team3 .team10 1
team3 .team11 1
team3 .team17 1
team3 .team18 1
team3 .team19 1
team3 .team20 1
team3 .team22 1
team4 .team9 1
team4 .team11 1
team4 .team12 1
team4 .team13 1
team4 .team17 1
team4 .team19 1
team4 .team20 1
team4 .team24 1
team5 .team9 1
team5 .team10 1
team5 .team12 1
team5 .team13 1
team5 .team14 1
team5 .team17 1
team5 .team23 1
team5 .team24 1
team6 .team12 1
team6 .team13 1
team6 .team14 1
team6 .team15 1
team6 .team18 1
team6 .team19 1
team6 .team21 1
team6 .team24 1
team7 .team11 1
team7 .team13 1
team7 .team15 1
team7 .team17 1
team7 .team18 1
team7 .team20 1
team7 .team22 1
team7 .team23 1
team8 .team10 1
team8 .team15 1
team8 .team17 1
team8 .team18 1
team8 .team20 1
team8 .team21 1
team8 .team23 1
team8 .team24 1
team9 .team17 1
team9 .team19 1
team9 .team24 1
team10.team18 1
team10.team19 1
team10.team22 1
team11.team20 1
team11.team21 1
team11.team22 1
team12.team19 1
team12.team20 1
team12.team21 1
team12.team23 1
team13.team21 1
team13.team22 1
team14.team19 1
team14.team22 1
team14.team23 1
team14.team24 1
team15.team18 1
team15.team20 1
team15.team21 1
team15.team23 1
team15.team24 1
team16.team17 1
team16.team18 1
team16.team19 1
team16.team20 1
team16.team21 1
team16.team22 1
team16.team23 1
team16.team24 1
+ round17 round18 round19 round20 round21 round22 round23
team1 .team2 1
team1 .team3 1
team1 .team4 1
team1 .team5 1
team1 .team6 1
team1 .team7 1
team1 .team8 1
team2 .team3 1
team2 .team4 1
team2 .team5 1
team2 .team6 1
team2 .team7 1
team2 .team8 1
team3 .team4 1
team3 .team5 1
team3 .team6 1
team3 .team7 1
team3 .team8 1
team4 .team5 1
team4 .team6 1
team4 .team7 1
team4 .team8 1
team5 .team6 1
team5 .team7 1
team5 .team8 1
team6 .team7 1
team6 .team8 1
team7 .team8 1
team9 .team10 1
team9 .team11 1
team9 .team12 1
team9 .team13 1
team9 .team14 1
team9 .team15 1
team9 .team16 1
team10.team11 1
team10.team12 1
team10.team13 1
team10.team14 1
team10.team15 1
team10.team16 1
team11.team12 1
team11.team13 1
team11.team14 1
team11.team15 1
team11.team16 1
team12.team13 1
team12.team14 1
team12.team15 1
team12.team16 1
team13.team14 1
team13.team15 1
team13.team16 1
team14.team15 1
team14.team16 1
team15.team16 1
team17.team18 1
team17.team19 1
team17.team20 1
team17.team21 1
team17.team22 1
team17.team23 1
team17.team24 1
team18.team19 1
team18.team20 1
team18.team21 1
team18.team22 1
team18.team23 1
team18.team24 1
team19.team20 1
team19.team21 1
team19.team22 1
team19.team23 1
team19.team24 1
team20.team21 1
team20.team22 1
team20.team23 1
team20.team24 1
team21.team22 1
team21.team23 1
team21.team24 1
team22.team23 1
team22.team24 1
team23.team24 1
This model solved very quickly, it needed about 0.2 seconds. Of course, the solution is not unique.
GAMS representation
set t 'team'/team1*team24/ r 'rounds'/round1*round23/ ; alias (t,t1,t2); set lt(t1,t2) 'less than'; lt(t1,t2) = ord(t1)<ord(t2); binaryvariable game(t1,t2,r) 'schedule for teams'; variable dummy 'objective variable'; equations round(r,t1) 'play exactly one opponent each round' meet(t1,t2) 't1 meets t2 exactly once' obj 'dummy objective' ; round(r,t1).. sum(lt(t1,t2),game(t1,t2,r))+sum(lt(t2,t1),game(t2,t1,r)) =e= 1; meet(lt(t1,t2)).. sum(r,game(t1,t2,r)) =e= 1; obj.. dummy=e=0; model m /all/; solve m minimizing dummy using mip; option game:0; display game.l; |
References
- Excel solver failure to get optimal solution when generating a schedule for 12 week schedule for 24 teams, https://stackoverflow.com/questions/62327762/excel-solver-failure-to-get-optimal-solution-when-generating-a-schedule-for-12-w
