This commit is contained in:
martin 2024-01-31 21:41:29 +01:00
parent cbcafaccbf
commit 6aac900d98
38 changed files with 34947 additions and 0 deletions

18
.gitignore vendored
View File

@ -167,3 +167,21 @@ solver/data/save_point/*
*.lp *.lp
*.mps *.mps
*.pptx *.pptx
*.svg
*.pdf
*.png
*.pulp
*.prt
*.log
*.cmd
*.attr
*.xlsx
*.xls
*.DS_Store
*.txt
*.stats
*.gexf
*.debug
*.sqlite3
*.ods
*.slx

135
draws/scripts/script.py Executable file
View File

@ -0,0 +1,135 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from django.shortcuts import HttpResponseRedirect
from django.http import HttpResponse, JsonResponse
from django.utils import timezone
from django.urls import reverse
from django.core.files.storage import FileSystemStorage
from django.core.mail import send_mail
from django_tex.shortcuts import render_to_pdf
from celery.result import AsyncResult
import googlemaps
import timeit
import random
import json
import builtins as __builtin__
import csv
from leagues.celery import celery
from leagues.settings import EMAIL_DEFAULT_FROM, EMAIL_DEFAULT_TO
from leagues.settings import RUN_ENV, INSTANCE, DEBUG
from common.tasks import log_telegram
from common.functions import *
from scheduler.models import *
from scheduler.helpers import *
from scheduler.widgets import widget_context_kpis
from scheduler.solver.optimizer import optimize_2phases, optimize_sequentially
import scheduler.solver.optimizer as so
from draws.solver import optimize_draws
from draws.models import *
import time as timer
# %%
scenario = Scenario.objects.get(id=9541)
conferences = Conference.objects.filter(scenario=scenario)
supergroups = SuperGroup.objects.filter(draw__season=scenario.season)
allgroups = Group.objects.filter(supergroup__in=supergroups)
sgGroups = { sg.id: [g.id for g in sg.groups.all()] for sg in supergroups }
# %%
for conference in conferences:
conference.teams.clear()
for sg in supergroups:
draw = sg.draw
season = sg.draw.season
g_name={ g.id : g.name for g in sg.groups.all() }
scen= False
scen = scenario
teamObjects= sg.teams.all().values()
t_name = {}
t_pot = {}
t_country = {}
for t in sg.teams.all():
t_name[t.id] = t.name
t_pot[t.id] = t.pot
t_country[t.id] = t.countryObj.shortname
teams = list (t_country.keys())
pots=sorted(list(set(t_pot.values())))
p_teams = { p: [t for t in teams if t_pot[t]==p] for p in pots}
maxpot = max([ t_pot[t] for t in teams])
sg_games_against_pot = sg.gamesPerTeam/maxpot
c_teams= { g.id: [] for g in allgroups }
for p in pots:
potTeams = p_teams[p]
random.shuffle(potTeams)
for t in potTeams:
allComments=""
candidates= sgGroups[sg.id]
minGroupLoad = min(len(c_teams[c]) for c in candidates)
cands = [c for c in candidates if len(c_teams[c]) == minGroupLoad]
c, r, b, fulldraw, comment, sol = optimize_draws.optimize_draws_New( scen.id, draw.id , t, cands, c_teams, [24, 25, 26, 27])
allComments+=comment
if p==1 or draw.alwaysPickFirstOpenGroup:
c=[c[0]]
chosen = random.choice(c)
c_teams[chosen].append(t)
allowedString=""
for g in c:
allowedString+=g_name[g][-1:]
if allComments!="":
allComments=";"+allComments.replace('\n',' ')
team = Team.objects.get(id=t)
conferences.filter(name=g_name[chosen]).first().teams.add(team)
# %%

View File

@ -0,0 +1,238 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "4d2a8b6c",
"metadata": {},
"source": [
"#### Database"
]
},
{
"cell_type": "code",
"execution_count": 1,
"id": "7be9eeff",
"metadata": {},
"outputs": [],
"source": [
"PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'\n",
"import os, sys\n",
"sys.path.insert(0, PROJECT_PATH)\n",
"os.environ.setdefault(\"DJANGO_SETTINGS_MODULE\", \"leagues.settings\")\n",
"\n",
"from leagues import settings\n",
"settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'\n",
"\n",
"import django\n",
"django.setup()\n",
"\n",
"from scheduler.models import *\n",
"from common.functions import distanceInKmByGPS\n",
"season = Season.objects.filter(nicename=\"Imported: Benchmark Season\").first()\n",
"import pandas as pd\n",
"import numpy as np\n",
"from django.db.models import Count, F, Value\n",
"games = Game.objects.filter(season=season)\n",
"df = pd.DataFrame.from_records(games.values())\n",
"games = Game.objects.filter(season=season).annotate(\n",
" home=F('homeTeam__shortname'),\n",
" away=F('awayTeam__shortname'),\n",
" home_lat=F('homeTeam__latitude'),\n",
" home_lon=F('homeTeam__longitude'),\n",
" home_attr=F('homeTeam__attractivity'),\n",
" away_lat=F('awayTeam__latitude'),\n",
" away_lon=F('awayTeam__longitude'),\n",
" away_attr=F('awayTeam__attractivity')\n",
").values()\n",
"\n"
]
},
{
"cell_type": "markdown",
"id": "bc191792",
"metadata": {},
"source": [
"#### Dataframe"
]
},
{
"cell_type": "code",
"execution_count": 2,
"id": "1e404cf8",
"metadata": {},
"outputs": [],
"source": [
"from sklearn.preprocessing import OneHotEncoder\n",
"\n",
"# create dataset\n",
"df = pd.DataFrame.from_records(games.values())\n",
"\n",
"# pivots\n",
"pivot_homeTeam_mean = df.pivot_table('attendance','homeTeam_id',aggfunc='mean')\n",
"pivot_homeTeam_max = df.pivot_table('attendance','homeTeam_id',aggfunc='max')\n",
"\n",
"# add more features\n",
"df['weekday'] = df.apply(lambda r: r['date'].weekday(), axis=1)\n",
"df['day'] = df.apply(lambda r: r['date'].day, axis=1)\n",
"df['month'] = df.apply(lambda r: r['date'].month, axis=1)\n",
"df['year'] = df.apply(lambda r: r['date'].year, axis=1)\n",
"df['distance'] = df.apply(lambda r: distanceInKmByGPS(r['home_lon'],r['home_lat'],r['away_lon'],r['away_lat']), axis=1)\n",
"df['weekend'] = df.apply(lambda r: int(r['weekday'] in [6,7]), axis=1)\n",
"df['winter_season'] = df.apply(lambda r: int(r['month'] in [1,2,3,10,11,12]), axis=1)\n",
"df['home_base'] = df.apply(lambda r: pivot_homeTeam_mean.loc[r['homeTeam_id'],'attendance'], axis=1)\n",
"df['stadium_size'] = df.apply(lambda r: pivot_homeTeam_max.loc[r['homeTeam_id'],'attendance'], axis=1)\n",
"\n",
"# one hot encoding\n",
"ohe_fields = ['time', 'historic_season']\n",
"\n",
"for field in ohe_fields:\n",
" ohe = OneHotEncoder()\n",
" transformed = ohe.fit_transform(df[[field]])\n",
" df[ohe.categories_[0]] = transformed.toarray()\n",
"\n",
"# sort label to last index\n",
"cols = list(df.columns)\n",
"cols.append(cols.pop(cols.index('attendance')))\n",
"df = df[cols]"
]
},
{
"cell_type": "code",
"execution_count": 3,
"id": "e69d24dc",
"metadata": {},
"outputs": [],
"source": [
"#Importing Libraries\n",
"import numpy as np # linear algebra\n",
"import pandas as pd # data processing\n",
"import matplotlib.pyplot as plt # plotting library\n",
"from sklearn.model_selection import train_test_split,cross_val_score, cross_val_predict\n",
"from sklearn import metrics\n",
"from sklearn.linear_model import LinearRegression\n",
"from sklearn.preprocessing import PolynomialFeatures\n",
"from sklearn.tree import DecisionTreeRegressor\n",
"from sklearn.ensemble import RandomForestRegressor"
]
},
{
"cell_type": "markdown",
"id": "e2ea08e5",
"metadata": {},
"source": [
"#### Train/Test Data - Normalization"
]
},
{
"cell_type": "code",
"execution_count": 4,
"id": "74e12f87",
"metadata": {},
"outputs": [],
"source": [
"from sklearn.model_selection import train_test_split\n",
"\n",
"\n",
"remove_columns = ['season_id', 'resultEntered', 'reversible', 'reschedule', 'homeGoals', 'awayGoals',\n",
" 'homeGoals2', 'awayGoals2', 'homeGoals3', 'awayGoals3', 'home', 'away', 'date', 'time', 'historic_season', 'id', 'homeTeam_id', 'awayTeam_id']\n",
"feature_cols = list(set(df.columns[:-1]) - set(remove_columns))\n",
"# feature_cols = ['weekday','weekend','home_base','distance','winter_season']\n",
"label = 'attendance'\n",
"\n",
"\n",
"X = df[feature_cols] # Features\n",
"y = df[label] # Target variable\n",
"\n",
"X_train, X_test, y_train, y_test = train_test_split(\n",
" X, y, test_size=0.3, random_state=1) # 70% training and 30% test"
]
},
{
"cell_type": "markdown",
"id": "94ade4b4",
"metadata": {},
"source": [
"#### Decision Tree"
]
},
{
"cell_type": "code",
"execution_count": 5,
"id": "4c9bdd0d",
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"FITTING...done\n",
"VISUALIZE\n"
]
},
{
"data": {
"text/plain": [
"True"
]
},
"execution_count": 5,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"import pydotplus\n",
"from six import StringIO\n",
"from sklearn.tree import export_graphviz\n",
"from sklearn.tree import DecisionTreeRegressor \n",
"from sklearn.preprocessing import OneHotEncoder\n",
"\n",
"# Create Decision Tree classifer object\n",
"regr = DecisionTreeRegressor(max_depth=5, random_state=1234)\n",
"\n",
"# Train Decision Tree Classifer\n",
"print(\"FITTING...\", end=\"\")\n",
"regr = regr.fit(X_train, y_train)\n",
"print(\"done\")\n",
"\n",
"# Predict the response for test dataset\n",
"y_pred = regr.predict(X_test)\n",
"\n",
"print(\"VISUALIZE\")\n",
"dot_data = StringIO()\n",
"export_graphviz(regr, out_file=dot_data,\n",
" filled=True, rounded=True,\n",
" special_characters=True, feature_names=feature_cols)\n",
"graph = pydotplus.graph_from_dot_data(dot_data.getvalue())\n",
"graph.write_png('attendance.png')\n",
"# Image(graph.create_png())"
]
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3.7.13 ('leagues')",
"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.7.13"
},
"vscode": {
"interpreter": {
"hash": "a07b7f3079ca8c056705d3c757c4f3f92f9509f33eeab9ad5420dacec37bc01a"
}
}
},
"nbformat": 4,
"nbformat_minor": 5
}

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1,295 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "4d2a8b6c",
"metadata": {},
"source": [
"#### Database"
]
},
{
"cell_type": "code",
"execution_count": 1,
"id": "7be9eeff",
"metadata": {},
"outputs": [],
"source": [
"PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'\n",
"import os, sys\n",
"sys.path.insert(0, PROJECT_PATH)\n",
"os.environ.setdefault(\"DJANGO_SETTINGS_MODULE\", \"leagues.settings\")\n",
"\n",
"from leagues import settings\n",
"settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'\n",
"\n",
"import django\n",
"django.setup()\n",
"\n",
"from scheduler.models import *\n",
"from common.functions import distanceInKmByGPS\n",
"season = Season.objects.filter(nicename=\"Imported: Benchmark Season\").first()\n",
"import pandas as pd\n",
"import numpy as np\n",
"from django.db.models import F\n",
"games = Game.objects.filter(season=season)\n",
"df = pd.DataFrame.from_records(games.values())\n",
"games = Game.objects.filter(season=season).annotate(\n",
" home=F('homeTeam__shortname'),\n",
" away=F('awayTeam__shortname'),\n",
" home_lat=F('homeTeam__latitude'),\n",
" home_lon=F('homeTeam__longitude'),\n",
" home_attr=F('homeTeam__attractivity'),\n",
" away_lat=F('awayTeam__latitude'),\n",
" away_lon=F('awayTeam__longitude'),\n",
" away_attr=F('awayTeam__attractivity'),\n",
" home_country=F('homeTeam__country'),\n",
" away_country=F('awayTeam__country'),\n",
").values()\n",
"\n"
]
},
{
"cell_type": "markdown",
"id": "bc191792",
"metadata": {},
"source": [
"#### Dataframe"
]
},
{
"cell_type": "code",
"execution_count": 2,
"id": "1e404cf8",
"metadata": {},
"outputs": [],
"source": [
"from sklearn.preprocessing import OneHotEncoder\n",
"\n",
"# create dataset\n",
"df = pd.DataFrame.from_records(games.values())\n",
"\n",
"# data cleaning\n",
"df['time'] = df['time'].replace('','0')\n",
"df = df[df['attendance'] != 0]\n",
"\n",
"\n",
"# pivots\n",
"pivot_homeTeam_mean = df.pivot_table('attendance','homeTeam_id',aggfunc='mean')\n",
"pivot_homeTeam_max = df.pivot_table('attendance','homeTeam_id',aggfunc='max')\n",
"\n",
"# add more features\n",
"df['weekday'] = df.apply(lambda r: r['date'].weekday(), axis=1)\n",
"df['day'] = df.apply(lambda r: r['date'].day, axis=1)\n",
"df['month'] = df.apply(lambda r: r['date'].month, axis=1)\n",
"df['year'] = df.apply(lambda r: r['date'].year, axis=1)\n",
"df['distance'] = df.apply(lambda r: distanceInKmByGPS(r['home_lon'],r['home_lat'],r['away_lon'],r['away_lat']), axis=1)\n",
"df['weekend'] = df.apply(lambda r: int(r['weekday'] in [6,7]), axis=1)\n",
"df['winter_season'] = df.apply(lambda r: int(r['month'] in [1,2,3,10,11,12]), axis=1)\n",
"df['home_base'] = df.apply(lambda r: pivot_homeTeam_mean.loc[r['homeTeam_id'],'attendance'], axis=1)\n",
"df['stadium_size'] = df.apply(lambda r: pivot_homeTeam_max.loc[r['homeTeam_id'],'attendance'], axis=1)\n",
"df['early'] = df.apply(lambda r: r['time'].replace(':','') < \"1800\", axis=1)\n",
"df['before2010'] = df.apply(lambda r: r['historic_season'].split('-')[0] < \"2010\", axis=1)\n",
"\n",
"\n",
"# one hot encoding\n",
"ohe_fields = ['home_country']\n",
"\n",
"for field in ohe_fields:\n",
" ohe = OneHotEncoder()\n",
" transformed = ohe.fit_transform(df[[field]])\n",
" df[ohe.categories_[0]] = transformed.toarray()\n",
"\n",
"# sort label to last index\n",
"cols = list(df.columns)\n",
"cols.append(cols.pop(cols.index('attendance')))\n",
"df = df[cols]"
]
},
{
"cell_type": "markdown",
"id": "e2ea08e5",
"metadata": {},
"source": [
"#### Train/Test Data - Normalization"
]
},
{
"cell_type": "code",
"execution_count": 3,
"id": "74e12f87",
"metadata": {},
"outputs": [],
"source": [
"import numpy as np \n",
"import pandas as pd \n",
"import matplotlib.pyplot as plt\n",
"import seaborn as sns\n",
"from sklearn.model_selection import train_test_split, cross_val_predict\n",
"from sklearn import metrics\n",
"from sklearn.ensemble import RandomForestRegressor\n",
"\n",
"\n",
"remove_columns = ['season_id', 'resultEntered', 'reversible', 'reschedule', 'homeGoals', 'awayGoals',\n",
" 'homeGoals2', 'awayGoals2', 'homeGoals3', 'awayGoals3', 'home', 'away', 'date', 'time',\n",
" 'id', 'homeTeam_id', 'awayTeam_id', 'historic_season',\n",
" 'home_country','home_lat','home_lon','away_lat','away_lon','away_country']\n",
"feature_cols = list(set(df.columns[:-1]) - set(remove_columns))\n",
"# feature_cols = ['weekday','weekend','home_base','distance','winter_season']\n",
"label = 'attendance'\n",
"\n",
"\n",
"X = df[feature_cols] # Features\n",
"y = df[label] # Target variable\n",
"\n",
"X_train, X_test, y_train, y_test = train_test_split(\n",
" X, y, test_size=0.3, random_state=1) # 70% training and 30% test"
]
},
{
"cell_type": "code",
"execution_count": 4,
"id": "53545faa",
"metadata": {},
"outputs": [],
"source": [
"import numpy as np \n",
"import pandas as pd \n",
"import matplotlib.pyplot as plt \n",
"import seaborn as sns \n",
"from sklearn.model_selection import train_test_split,cross_val_score, cross_val_predict\n",
"from sklearn import metrics\n",
"from sklearn.linear_model import LinearRegression\n",
"from sklearn.preprocessing import PolynomialFeatures\n",
"from sklearn.tree import DecisionTreeRegressor\n",
"from sklearn.ensemble import RandomForestRegressor"
]
},
{
"cell_type": "code",
"execution_count": 5,
"id": "45e08026",
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Mutiple Linear Regression Accuracy: 0.3819963751047786\n",
"Cross-Predicted(KFold) Mutiple Linear Regression Accuracy: 0.33440778552391626\n"
]
}
],
"source": [
"lin_reg = LinearRegression()\n",
"lin_reg.fit(X_train,y_train)\n",
"\n",
"#Predicting the SalePrices using test set \n",
"y_pred_lr = lin_reg.predict(X_test)\n",
"\n",
"#Mutiple Linear Regression Accuracy with test set\n",
"accuracy_lf = metrics.r2_score(y_test, y_pred_lr)\n",
"print('Mutiple Linear Regression Accuracy: ', accuracy_lf)\n",
"\n",
"#Predicting the SalePrice using cross validation (KFold method)\n",
"y_pred_kf_lr = cross_val_predict(lin_reg, X, y, cv=10 )\n",
"\n",
"#Mutiple Linear Regression Accuracy with cross validation (KFold method)\n",
"accuracy_lf = metrics.r2_score(y, y_pred_kf_lr)\n",
"print('Cross-Predicted(KFold) Mutiple Linear Regression Accuracy: ', accuracy_lf)"
]
},
{
"cell_type": "code",
"execution_count": 6,
"id": "0de49b8a",
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Cross-Predicted(KFold) Polynominal Regression Accuracy: -261.39170432313074\n"
]
}
],
"source": [
"poly_reg = PolynomialFeatures(degree = 2)\n",
"X_poly = poly_reg.fit_transform(X)\n",
"lin_reg_pl = LinearRegression()\n",
"\n",
"#Predicting the SalePrice using cross validation (KFold method)\n",
"y_pred_pl = cross_val_predict(lin_reg_pl, X_poly, y, cv=10 )\n",
"#Polynominal Regression Accuracy with cross validation\n",
"accuracy_pl = metrics.r2_score(y, y_pred_pl)\n",
"print('Cross-Predicted(KFold) Polynominal Regression Accuracy: ', accuracy_pl)"
]
},
{
"cell_type": "code",
"execution_count": 7,
"id": "470425b6",
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Decision Tree Regression Accuracy: 0.23642868476932866\n",
"Cross-Predicted(KFold) Decision Tree Regression Accuracy: 0.4183541357709245\n"
]
}
],
"source": [
"dt_regressor = DecisionTreeRegressor(random_state = 0)\n",
"dt_regressor.fit(X_train,y_train)\n",
"\n",
"#Predicting the SalePrices using test set \n",
"y_pred_dt = dt_regressor.predict(X_test)\n",
"\n",
"#Decision Tree Regression Accuracy with test set\n",
"print('Decision Tree Regression Accuracy: ', dt_regressor.score(X_test,y_test))\n",
"\n",
"#Predicting the SalePrice using cross validation (KFold method)\n",
"y_pred_dt = cross_val_predict(dt_regressor, X, y, cv=10 )\n",
"#Decision Tree Regression Accuracy with cross validation\n",
"accuracy_dt = metrics.r2_score(y, y_pred_dt)\n",
"print('Cross-Predicted(KFold) Decision Tree Regression Accuracy: ', accuracy_dt)"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "6629826f",
"metadata": {},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3.7.13 ('leagues')",
"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.7.13"
},
"vscode": {
"interpreter": {
"hash": "a07b7f3079ca8c056705d3c757c4f3f92f9509f33eeab9ad5420dacec37bc01a"
}
}
},
"nbformat": 4,
"nbformat_minor": 5
}

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,312 @@
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
import django
django.setup()
from scheduler.models import *
from common.functions import distanceInKmByGPS
import pandas as pd
import numpy as np
from django.db.models import Count, F, Value
thisScenario = Scenario.objects.get(id = 2)
thisSeason = thisScenario.season
thisLeague = thisSeason.league
mathModelName=thisLeague.name
if thisSeason.optimizationParameters!="":
mathModelName=thisSeason.optimizationParameters
otherScenGames=[]
if thisSeason.improvementObjective!="--":
for otherScenario in Scenario.objects.filter(season=thisSeason):
impObjWeight = 5
if thisSeason.improvementObjective=="stick to old solutions":
impObjWeight = -5
if otherScenario.solutionlist() != [['']]:
for g in otherScenario.solutionlist():
otherScenGames.append((int(g[1]),int(g[2]),int(g[3]), impObjWeight ))
getGlobalCountry={ gc['uefa']: gc['id'] for gc in GlobalCountry.objects.values() }
teamObjects = Team.objects.filter(season=thisSeason,active=True).order_by('position').values()
teams=[]
realteams=[]
faketeams=[]
importantteams=[]
shortteams=[]
t_pos={}
t_pot={}
t_color={}
t_country={}
t_globalCountry={}
t_stadium = {}
t_shortname = {}
t_usePhases = {}
t_lon = {}
t_lat = {}
t_attractivity ={}
getTeamById={}
getTeamIdByName={}
getTeamIdByShortName={}
getTeamByName={}
getStadiumById={}
teamByShort={}
top4 = []
for t in teamObjects:
# print (t['name'], t['id'])
teams.append(t['id'])
shortteams.append(t['shortname'])
teamByShort[t['shortname']]= t['name']
getTeamIdByShortName[t['shortname']]=t['id']
if t['name']!='-':
realteams.append(t['id'])
else:
faketeams.append(t['id'])
if t['very_important']:
importantteams.append(t['id'])
t_country[t['id']]= t['country']
t_globalCountry[t['id']]= t['globalCountry_id']
if not t_globalCountry[t['id']] and t_country[t['id']] in getGlobalCountry.keys() :
t_globalCountry[t['id']] = getGlobalCountry[t_country[t['id']]]
t_pos[t['name']]= t['position']
t_color[t['name']]="lightyellow"
t_pot[t['id']]= t['pot']
t_stadium[t['id']]=t['stadium']
t_attractivity[t['id']]=t['attractivity']
t_lon[t['id']]=t['longitude']
t_lat[t['id']]=t['latitude']
t_shortname[t['id']]=t['shortname']
t_usePhases[t['id']]= thisScenario.usePhases
getTeamById[t['id']]=t['name']
getStadiumById[t['id']]=t['stadium']
getTeamIdByName[t['name']]=t['id']
getTeamByName[t['name']]=t
if t['attractivity'] >= thisSeason.topTeamMinCoefficient :
top4.append(t['id'])
inactive_teams=[]
for t in Team.objects.filter(season=thisSeason,active=False).order_by('position').values():
inactive_teams.append(t['id'])
t_attractivity[t['id']]=t['attractivity']
t_lon[t['id']]=t['longitude']
t_lat[t['id']]=t['latitude']
t_country[t['id']]= t['country']
getTeamById[t['id']]=t['name']
lowerBoundFound = False
distance ={}
attractivity ={}
distanceById={}
distanceInDaysById={}
stadium_names = set([t['stadium'] for t in teamObjects if t['stadium']!=''])
stadium_id={}
stadium_name={}
sid=0
for stadium in stadium_names :
stadium_name[sid]=stadium
stadium_id[stadium]=sid
sid+=1
stadiums = list(stadium_name.keys())
teamsOfStadium ={ st:[] for st in stadiums }
travelDict= thisSeason.travelDict()
for t1 in teamObjects:
if t1['stadium']!='':
teamsOfStadium[stadium_id[t1['stadium']]].append(t1['id'])
for t2 in teamObjects:
# distance[t1['name'],t2['name']] = distanceInKm(t1,t2)
# print (t1['name'],t2['name'],distance[t1['name'],t2['name']] ," -> ", travelDict[t1['id']][t2['id']]['distance'] )
distance[t1['name'],t2['name']] = travelDict[t1['id']][t2['id']]['distance']
distanceById[t1['id'],t2['id']] = distance[t1['name'],t2['name']]
distanceInDaysById[t1['id'],t2['id']] = int(distance[t1['name'],t2['name']]/350 +0.99)
attractivity[t1['id'],t2['id']] = int(100*t1['attractivity']*t2['attractivity'])
dayObjects = Day.objects.filter(season=thisSeason).values()
days = [ d['id'] for d in dayObjects if d['round']>0 ]
higherSeasons = thisSeason.higherSeasons()
higherGames = thisSeason.higherGames()
this_season_team_names = list(getTeamByName.keys())
higherTeamObjects = Team.objects.filter(season__in=higherSeasons,active=True).values()
higherDayObjects = Day.objects.filter(season__in=higherSeasons,maxGames__gte=1).values()
higherTeams = [ t['id'] for t in higherTeamObjects]
higherTeamsOf={ t: [] for t in teams}
for t in higherTeamObjects:
getTeamById[t['id']]=t['name']
t_country[t['id']]=t['country']
if t['name'] in this_season_team_names:
higherTeamsOf[getTeamIdByName[t['name']]].append(t['id'])
print ("Teams : " , teams)
print ("VIP Teams : " , importantteams)
print ("TOP Teams : " , top4)
allConferences = Conference.objects.filter(scenario=s2)
sharedStadiums = False
for ff in thisSeason.federationmember.all():
sharedStadiums= ff.federation.sharedStadiums
# print ("\nGroups : ")
t_conference = {t : 0 for t in teams }
conf_teams={}
for c in Conference.objects.filter(scenario=s2,regional=False).order_by('name'):
# print ("A" , c)
cteams = c.teams.filter(active=True)
conf_teams[c.name]=[]
for t in cteams:
conf_teams[c.name].append(t.id)
# print ("group for ", t)
# if t_conference[t.id]!=0:
# print (getTeamById[t.id] , " in several groups")
if t_conference[t.id]==0 or len(cteams)< len(t_conference[t.id].teams.filter(active=True)):
t_conference[t.id]=c
# print (" is " , c )
# for t in set([t for t in teams if t_conference[t]==0 ]):
# print (" no group " , getTeamById[ t])
# return ''
prioVal ={'A': 25 , 'B': 5 , 'C': 1, 'Hard' : 1000}
sw_prio = {}
sw_float1 = {}
sw_float2 = {}
sw_int1 = {}
sw_int2 = {}
sw_text = {}
for sw in SpecialWish.objects.filter(scenario=s2):
sw_prio[sw.name]=prioVal[sw.prio] if sw.active else 0
sw_float1[sw.name]=sw.float1
sw_float2[sw.name]=sw.float2
sw_int1[sw.name]=sw.int1
sw_int2[sw.name]=sw.int2
sw_text[sw.name]=sw.text
special_wishes=list(sw_prio.keys())
special_wishes_active = [ sw for sw in special_wishes if sw_prio[sw]>0 ]
print (special_wishes_active)
noBreakLimitTeams = []
if "allowManyBreaksInRow" in special_wishes_active :
noBreakLimitTeams = sw_text["allowManyBreaksInRow"].split(",")
print (noBreakLimitTeams)
noBreakLimitTeams = [t for t in teams if getTeamById[t] in noBreakLimitTeams]
print (noBreakLimitTeams)
pairings_tmp = Pairing.objects.filter(scenario=s2, active=True).values()
pairings_tmp2 = Pairing.objects.filter(scenario__is_published=True, team1__id__in=teams, team2__id__in=higherTeams, active=True).values()
pairings_tmp3 = Pairing.objects.filter(scenario__is_published=True, team2__id__in=teams, team1__id__in=higherTeams, active=True).values()
pairings = []
for p in [ p for p in pairings_tmp if p['team1_id'] in teams and p['team2_id'] in teams+higherTeams ] + [ p for p in pairings_tmp2 ] + [ p for p in pairings_tmp3]:
if p not in pairings:
pairings.append(p)
breaks = Break.objects.filter(season=thisSeason).values()
blockings_tmp = Blocking.objects.filter(scenario=s2,active=True).values()
blockings = [ bl for bl in blockings_tmp if bl['team_id'] in teams ]
# times = ['Early', 'Late']
timeObjects = TimeSlot.objects.filter(season=thisSeason).values()
times = [ str(t['id']) for t in timeObjects]
getTimeById = {str(t['id']):t['name'] for t in timeObjects}
getIdByTime = {t['name']:str(t['id']) for t in timeObjects}
blocked_arena = {(t,d, tm) : False for t in teams for d in days for tm in ["----"] + times }
hidden_arena = {(t,d, tm) : False for t in teams for d in days for tm in ["----"] + times }
nBlockingHome=0
nBlockingAway=0
for bl in blockings:
if bl['type'] in ["Hide"]:
hidden_arena[(bl['team_id'],bl['day_id'], bl['time'] )]=True
if bl['type'] in ["Home","Hide"]:
nBlockingHome+=1
blocked_arena[(bl['team_id'],bl['day_id'], bl['time'] )]=True
else:
nBlockingAway+=1
nTeams=len(teams)
nPhases =thisSeason.numPhases
groupView = thisSeason.groupBased
gameCntr={(t1,t2) : 0 for t1 in teams for t2 in teams}
undirectedGameCntr={(t1,t2) : 0 for t1 in teams for t2 in teams}
if thisSeason.useFeatureOpponentMatrix:
gameRequirements = GameRequirement.objects.filter(season=thisSeason, team1__active=True, team2__active=True)
# print (len(gameRequirements))
for gm in gameRequirements:
if thisSeason.undirectedGames:
undirectedGameCntr[(gm.team1.id,gm.team2.id)]+=gm.number
undirectedGameCntr[(gm.team2.id,gm.team1.id)]+=gm.number
# print ( "found undirected game " , (gm.team1.id,gm.team2.id) , gm.number )
else:
gameCntr[(gm.team1.id,gm.team2.id)]+=gm.number
# print ( "found directed game " , (gm.team1.id,gm.team2.id) , gm.number )
else:
for t1 in teams:
for t2 in teams:
if t1!=t2:
gameCntr[(t1,t2)]+=nPhases/2
for c in Conference.objects.filter(scenario=s2):
cteams = c.teams.filter(active=True)
for t1 in cteams:
for t2 in cteams:
if t1!=t2:
gameCntr[(t1.id,t2.id)]+=c.deltaGames/2
for (t1,t2) in gameCntr.keys():
if gameCntr[(t1,t2)]%1!=0 :
undirectedGameCntr[(t1,t2)]=1
gameCntr[(t1,t2)] = int(gameCntr[(t1,t2)])
games = [ gm for gm in gameCntr.keys() if gameCntr[gm]+undirectedGameCntr[gm]>0]
objectiveFunctionWeights = ObjectiveFunctionWeight.objects.filter(scenario=s2).values()
gew={}
gew['Trips'] = 5
gew['Derbies'] = 5
gew['Pairings'] = 5
for ow in objectiveFunctionWeights:
gew[ow['name']]= ow['use'] * ow['prio']
objectivePrio = 'Breaks'
if gew['Trips']>gew['Breaks'] :
objectivePrio = 'Trips'
print("objectivePrio:", objectivePrio)
specialGameControl= mathModelName in ["Florida State League"]
if len(games)==0:
games = [ (t1,t2) for t1 in teams for t2 in teams if t1!=t2 ]
specialGameControl=True
realgames= [(t1,t2) for (t1,t2) in games if getTeamById[t1]!="-" and getTeamById[t2]!="-"]
# nur wenn die solutionlist alle spiele enthält, wird dieser modus aktiviert
evalRun = ( runMode == "Improve" and localsearch_time==0
and len(thisScenario.solutionlist())==sum([gameCntr[gm]+0.5*undirectedGameCntr[gm] for gm in realgames]) )
opponents = { t: set([]) for t in realteams}
for (t1,t2) in games:
if t1 in realteams and t2 in realteams:
opponents[t1].add(t2)
opponents[t2].add(t1)

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,122 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
import django
django.setup()
from scheduler.models import *
from pulp import *
from django.urls import get_resolver
from django_tex.shortcuts import render_to_pdf
from common import urls
from referees import urls
from qualifiers import urls
from django.core.handlers.base import BaseHandler
from django.test.client import RequestFactory
from scheduler.widgets import widget_context_games_reduced
# %%
scenario = Scenario.objects.get(id=14)
dayObjects = Day.objects.filter(season=scenario.season)
rounds = dict(scenario.gamesOfRound()).keys()
teams = scenario.teams_dict()
timeslots = {str(t.id):t.name for t in scenario.season.timeslots.all()}
getTeamById = {}
teamObj = Team.objects.filter(season=scenario.season)
for t in teamObj:
getTeamById[str(t.id)] = t
if (t.logo.name.split('.')[-1] != 'png'):
os.rename(f'{t.logo.path}',f'{t.logo.path}.png')
t.logo.name = f'{t.logo.name}.png'
t.save()
# %%
getDayById = {}
for d in dayObjects:
getDayById[d.id] = d
list_games = []
list_rounds = {r:defaultdict(lambda:[]) for r in rounds}
list_days = defaultdict(lambda:[])
games = {}
cntr = 0
x_pos = 0
y_pos = 0
last_y_pos = 0
page_break = 9999
for r in rounds:
games[r] = widget_context_games_reduced(scenario,r)
games_per_round = 0
if last_y_pos + sum([len(i) for i in games[1]['gamesOfDay'].values()]) > 60:
page_break = x_pos
last_y_pos = 0
x_pos = 0
y_pos = last_y_pos+10
for day,gamesPerDay in games[r]['gamesOfDay'].items():
if not gamesPerDay:
continue
for game in gamesPerDay:
games_per_round += 1
cntr += 1
t1 = getTeamById[game[1]]
t2 = getTeamById[game[2]]
game_details = (f'{cntr}','',f'\includegraphics[width=0.2cm]{{{t1.logo.path}}}',f'{t1.shortname}', f'\includegraphics[width=0.2cm]{{{t2.logo.path}}}', f'{t2.shortname}',x_pos % 5,y_pos,game[4])
list_games.append(game_details)
list_rounds[r][(day,str(getDayById[day]))].append(game_details)
list_days[str(getDayById[day])].append(game_details)
y_pos += 1
y_pos += 3
x_pos += 1
if x_pos % 5 == 0:
last_y_pos = y_pos
if x_pos >= page_break:
last_y_pos = 0
x_pos = 0
# %%
template_name = 'latex/season_overview.tex'
context = {
'scenario': scenario,
'rounds': list_rounds,
'page_break':page_break,
}
response = render_to_pdf(None, template_name, context, filename='test.pdf')
with open("response.pdf", "wb") as f:
f.write(response.content)
# %%

165
qualifiers/scripts/debug.py Executable file
View File

@ -0,0 +1,165 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
# settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
# settings.DATABASES['default']['HOST'] = '0.0.0.0'
# settings.DATABASES['default']['PORT'] = '5432'
# settings.DATABASES['default']['USER'] = 'postgres'
# settings.DATABASES['default']['PASSWORD'] = 'secret123'
# settings.DATABASES['default']['NAME'] = 'mypgsqldb'
# settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
# settings.DATABASES['default']['AUTOCOMMIT'] = True
# settings.DATABASES['default']['CONN_MAX_AGE'] = 0
# settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
# settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from django.shortcuts import HttpResponseRedirect
from django.http import HttpResponse, JsonResponse
from django.utils import timezone
from django.urls import reverse
from django.core.files.storage import FileSystemStorage
from django.core.mail import send_mail
from django_tex.shortcuts import render_to_pdf
from celery.result import AsyncResult
import googlemaps
import timeit
import random
import json
import builtins as __builtin__
import csv
from leagues.celery import celery
from leagues.settings import EMAIL_DEFAULT_FROM, EMAIL_DEFAULT_TO
from leagues.settings import RUN_ENV, INSTANCE, DEBUG
from common.tasks import log_telegram
from common.functions import *
from scheduler.models import *
from scheduler.helpers import *
from scheduler.widgets import widget_context_kpis
from scheduler.solver.optimizer import optimize_2phases, optimize_sequentially
import scheduler.solver.optimizer as so
from draws.solver import optimize_draws
import time as timer
from qualifiers.helpers import import_globals
# %%
scenario = Scenario.objects.get(id=1)
# import_globals(scenario.season.id)
# teams = scenario.season.scheduler_teams.all()
# %%
new_teams = []
new_teams.append((1, "Manchester City FC (ENG)", 145.000, "Pot 1",5,4))
new_teams.append((2, "FC Bayern München (GER)", 136.000, "Pot 1",5,5))
new_teams.append((3, "Liverpool FC (ENG)", 123.000, "Pot 1",5,5))
new_teams.append((4, "Real Madrid CF (ESP)", 121.000, "Pot 1",5,5))
new_teams.append((5, "Paris Saint-Germain (FRA)", 112.000, "Pot 1",5,5))
new_teams.append((6, "Manchester United FC (ENG)", 104.000, "Pot 1",5,5))
new_teams.append((7, "FC Barcelona (ESP)", 98.000, "Pot 1",5,5))
new_teams.append((8, "FC Internazionale Milano (ITA)", 96.000, "Pot 1",4,5))
new_teams.append((9, "Sevilla FC (ESP)", 91.000, "Pot 1",3,4))
new_teams.append((10, "Borussia Dortmund (GER)", 86.000, "Pot 2",4,4))
new_teams.append((11, "Club Atlético de Madrid (ESP)", 85.000, "Pot 2",4,4))
new_teams.append((12, "RB Leipzig (GER)", 84.000, "Pot 2",3,3))
new_teams.append((13, "SL Benfica (POR)", 82.000, "Pot 2",2,5))
new_teams.append((14, "SSC Napoli (ITA)", 81.000, "Pot 2",3,4))
new_teams.append((15, "FC Porto (POR)", 81.000, "Pot 2",3,5))
new_teams.append((16, "Arsenal FC (ENG)", 76.000, "Pot 2",4,4))
new_teams.append((17, "FC Shakhtar Donetsk (UKR)", 63.000, "Pot 2",1,5))
new_teams.append((18, "FC Salzburg (AUT)", 59.000, "Pot 2",2,5))
new_teams.append((19, "Atalanta BC (ITA)", 55.500, "Pot 3",2,3))
new_teams.append((20, "Feyenoord (NED)", 51.000, "Pot 3",2,4))
new_teams.append((21, "AC Milan (ITA)", 50.000, "Pot 3",3,5))
new_teams.append((22, "SC Braga (POR)", 44.000, "Pot 3",2,3))
new_teams.append((23, "PSV Eindhoven (NED)", 43.000, "Pot 3",2,4))
new_teams.append((24, "S.S. Lazio (ITA)", 42.000, "Pot 3",2,3))
new_teams.append((25, "FK Crvena zvezda (SRB)", 42.000, "Pot 3",1,5))
new_teams.append((26, "F.C. Copenhagen (DEN)", 40.500, "Pot 3",1,4))
new_teams.append((27, "BSC Young Boys (SUI)", 34.500, "Pot 3",1,4))
new_teams.append((28, "Real Sociedad de Fútbol (ESP)", 33.000, "Pot 4",2,3))
new_teams.append((29, "Olympique de Marseille (FRA)", 33.000, "Pot 4",3,4))
new_teams.append((30, "Galatasaray A.Ş. (TUR)", 31.500, "Pot 4",1,5))
new_teams.append((31, "Celtic FC (SCO)", 31.000, "Pot 4",2,3))
new_teams.append((32, "Qarabağ FK (AZE)", 25.000, "Pot 4",1,5))
new_teams.append((33, "Newcastle United FC (ENG)", 21.914, "Pot 4",3,3))
new_teams.append((34, "1. FC Union Berlin (GER)", 17.000, "Pot 4",2,3))
new_teams.append((35, "R. Antwerp FC (BEL)", 17.000, "Pot 4",3,3))
new_teams.append((36, "RC Lens (FRA)", 12.232, "Pot 4",2,3))
CET_minus_1 = ['ENG','POR','SCO']
CET_plus_1 = ['TUR','AZE','ISR','UKR']
# %%
for conf in Conference.objects.filter(scenario=scenario).exclude(name__in=['HARD Constraints','SOFT Constraints']):
conf.teams.clear()
Team.objects.filter(season=scenario.season).update(active=False)
for t in new_teams:
team_name = t[1].split('(')[0].strip()
team_country = t[1].split('(')[1].split(')')[0].strip()
global_coeff = t[4]
domestic_coeff = t[5]
teamObj = Team.objects.filter(name=team_name)
if teamObj:
Conference.objects.filter(scenario=scenario,name="UCL").first().teams.add(teamObj.first())
Conference.objects.filter(scenario=scenario,name=t[3]).first().teams.add(teamObj.first())
if global_coeff in [3,4,5]:
Conference.objects.filter(scenario=scenario,name=f"Global Coeff {global_coeff}").first().teams.add(teamObj.first())
if domestic_coeff in [3,5]:
Conference.objects.filter(scenario=scenario,name=f"Domestic coeff {domestic_coeff}").first().teams.add(teamObj.first())
if team_country in CET_minus_1:
Conference.objects.filter(scenario=scenario,name="CET-1").first().teams.add(teamObj.first())
elif team_country in CET_plus_1:
Conference.objects.filter(scenario=scenario,name="CET+1").first().teams.add(teamObj.first())
else:
Conference.objects.filter(scenario=scenario,name="CET").first().teams.add(teamObj.first())
teamObj.update(active=True)
teamObj.update(attractivity=global_coeff)
teamObj.update(position=t[0])
pass
else:
print(t,"->", team_name)
# %%

View File

@ -0,0 +1,72 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
import django
django.setup()
from scheduler.models import *
from pulp import *
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
import random
import time
import json
import csv
# %%
from django.contrib.sessions.models import Session
scenario = Scenario.objects.get(id=8938)
# %%
from scheduler.solver.tasks.optimize import optimize
s2 = scenario.id
user_name = 'md'
user_is_staff = True
localsearch_time = 30
RUN_ENV = 'local'
SOLVER = 'xpress'
sol = optimize(task=None, s2=s2, user_name=user_name, user_is_staff=user_is_staff,
runMode='Improve', localsearch_time=localsearch_time, RUN_ENV=RUN_ENV, solver=SOLVER)
# %%

View File

@ -0,0 +1,91 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_develop/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
# settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
# settings.DATABASES['default']['HOST'] = '0.0.0.0'
# settings.DATABASES['default']['PORT'] = '5432'
# settings.DATABASES['default']['USER'] = 'postgres'
# settings.DATABASES['default']['PASSWORD'] = 'secret123'
# settings.DATABASES['default']['NAME'] = 'mypgsqldb'
# settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
# settings.DATABASES['default']['AUTOCOMMIT'] = True
# settings.DATABASES['default']['CONN_MAX_AGE'] = 0
# settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
# settings.DATABASES['default']['OPTIONS'] = {}
# os.environ["XPRESSDIR"] = "/opt/xpressmp"
# os.environ["XPRESS"] = "/opt/xpressmp/bin"
# os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
# os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
# os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
# os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
# os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
# os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
# os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
# os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
# os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.tasks.optimize import optimize
from referees.helpers import use_referees, import_deb_delegates, seed_rounds_from_days, generate_distance_matrix
from referees.models import RefGame, Role
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from datetime import timedelta
# %%
scenario = Scenario.objects.get(id=24)
# %%
# use_referees(scenario.id)
import_deb_delegates(scenario)
generate_distance_matrix(scenario.season.id)
# %%
# season = scenario.season
# %%
# seed_rounds_from_days(scenario.season.id)
# Role.objects.all().delete()
# Role.objects.create(season=season, name="Referee", min_required=2, max_required=2)
# Role.objects.create(season=season,name="Linesmen", min_required=2, max_required=2)
# %%

127
referees/scripts/script_wales.py Executable file
View File

@ -0,0 +1,127 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_develop/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, Day, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.tasks.optimize import optimize
from common.functions import distanceInMilesByGPS
from referees.helpers import use_referees, import_deb_delegates, seed_rounds_from_days, generate_distance_matrix
from referees.models import *
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from dateutil import parser
from datetime import timedelta
import googlemaps
import pandas as pd
# %%
scenario = Scenario.objects.get(id=4)
season= scenario.season
# %%
# from referees.optimize import optimize_referees, optimize_referees_reopt, optimize_delegates, optimize_wales
# sol=optimize_wales(scenario.id, "md", True, RUN_ENV='NO_CELERY')
# %%
tt = time.time()
for d in Delegate.objects.filter(season=season).prefetch_related('assignments'):
# for d in Delegate.objects.filter(season=season).prefetch_related('assignments').only('id'):
# for d in Delegate.objects.filter(season=season):
for a in d.assignments.all():
x = a.travel
print(time.time()-tt)
# %%
# categories = Category.objects.filter(season=season,requirements__in=Requirement.objects.filter(season=season))
# delegates = Delegate.objects.filter(season=season,active=True,category__in=categories)
# Delegate.objects.filter(season=season).exclude(id__in=delegates.values('id')).update(active=False)
# for d in Delegate.objects.filter(season=season):
# if d.location:
# d.latitude = d.location.latitude
# d.longitude = d.location.longitude
# d.save()
# %%
# for d in Delegate.objects.filter(season=season):
# d.name = f"Person {d.name}"
# d.save()
# # %%
# competitions = Competition.objects.filter(season=season)
# days = Day.objects.filter(season=season).exclude(round=7)
# # %%
# for d in Delegate.objects.filter(season=season):
# d.coefficient = d.category.order
# d.save()
# from referees.optimize import optimize_referees, optimize_referees_reopt, optimize_delegates, optimize_wales
# sol=optimize_wales(2, "md", True, RUN_ENV='NO_CELERY')
# # %%
# ranks = [
# 'Elite Group One',
# 'Elite Group Two',
# '2',
# '3',
# '4A',
# '4B',
# '4C',
# '4D',
# 'AJR',
# 'CJR',
# 'International AR (FIFA List)',
# '1AR',
# '1ART',
# '2AR',
# '3AR',
# ]
# for i,r in enumerate(ranks):
# Category.objects.filter(name=r).update(order=i+1)
# # %%
# for d in Delegate.objects.filter(season=season):
# group,_ = DelGroup.objects.get_or_create(season=season, name=d.category)
# group.delegates.add(d)
# %%

323
referees/scripts/seed_wales.py Executable file
View File

@ -0,0 +1,323 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_develop/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
# settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
# settings.DATABASES['default']['HOST'] = '0.0.0.0'
# settings.DATABASES['default']['PORT'] = '5432'
# settings.DATABASES['default']['USER'] = 'postgres'
# settings.DATABASES['default']['PASSWORD'] = 'secret123'
# settings.DATABASES['default']['NAME'] = 'mypgsqldb'
# settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
# settings.DATABASES['default']['AUTOCOMMIT'] = True
# settings.DATABASES['default']['CONN_MAX_AGE'] = 0
# settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
# settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, Day, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.tasks.optimize import optimize
from common.functions import distanceInMilesByGPS
import datetime
from referees.helpers import use_referees, import_deb_delegates, seed_rounds_from_days, generate_distance_matrix
from referees.models import *
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from dateutil import parser
from datetime import timedelta
import googlemaps
import pandas as pd
# %%
gmaps = googlemaps.Client(key='AIzaSyB76EhR4OqjdXHQUiTkHZC0Svx_7cPGqyU')
scenario = Scenario.objects.get(id=4)
season= scenario.season
# %%
# def seed_stadiums():
# df = pd.read_excel('referees/fixtures/wales/List_of_stadiums1700843463152.xlsx')
# Location.objects.filter(season=scenario.season).delete()
# for index, row in df.iterrows():
# name = row['Name']
# country = row['Country']
# city= row['Place']
# longitude = row['invisible_label_longitude']
# latitude = row['invisible_label_latitude']
# country_obj = Country.objects.filter(season=scenario.season,name=country).first()
# if not pd.isna(row['invisible_label_latitude']) and not pd.isna(row['invisible_label_longitude']):
# Location.objects.create(name=row['Name'],city=city,country=country_obj, latitude=row['invisible_label_latitude'], longitude=row['invisible_label_longitude'], season=season)
# else:
# geocode_result = gmaps.geocode(f"{country}+{city}+{name}")
# if len(geocode_result) > 0:
# lat = geocode_result[0]['geometry']['location']['lat']
# lng = geocode_result[0]['geometry']['location']['lng']
# Location.objects.create(name=row['Name'],city=city,country=country_obj, latitude=lat, longitude=lng, season=season)
# seed_stadiums()
# %%
# def seed_delegates():
# df = pd.read_excel('referees/fixtures/wales/Anonymised Referee Registrations for Ligalytics.xlsx')
# country = Country.objects.get(season=season,name='Wales')
# Delegate.objects.filter(season=season).delete()
# Role.objects.filter(season=season).delete()
# Role.objects.create(order=1,name='Referee', season=season)
# Role.objects.create(order=2,name='Assistant Referee 1', season=season)
# Role.objects.create(order=3,name='Assistant Referee 2', season=season)
# Role.objects.create(order=4,name='Fourth Official', season=season)
# for index, row in df.iterrows():
# name = row['Dummy ID']
# city = row['Home Town']
# category = row['Refеree category']
# cat = Category.objects.filter(name=category, season=season).first()
# if not cat:
# cat = Category.objects.create(name=category, season=season)
# location = Location.objects.filter(name=city, country=country).first()
# if not location:
# geocode_result = gmaps.geocode(f"{country}+{city}")
# if len(geocode_result) > 0:
# lat = geocode_result[0]['geometry']['location']['lat']
# lng = geocode_result[0]['geometry']['location']['lng']
# location = Location.objects.create(name=city,city=city,country=country, latitude=lat, longitude=lng, season=season, type=3)
# else:
# print("No geocode for ", city)
# # role = Role.objects.filter(season=season,name=category).first()
# # if not role:
# # role = Role.objects.create(name=category, season=season)
# delegate = Delegate.objects.create(name=name, country=country, location=location, category=cat, season=season)
# seed_delegates()
# %%
# def seed_teams_and_games():
# matches = pd.read_excel('referees/fixtures/wales/v2/Matches Test December 2023.xlsx') #.set_index('Name')
# country = Country.objects.get(season=season,name='Wales')
# Team.objects.filter(season=season).delete()
# Day.objects.filter(season=season).delete()
# Round.objects.filter(season=season).delete()
# Game.objects.filter(season=season).delete()
# RefGame.objects.filter(scenario=scenario).delete()
# Competition.objects.filter(season=season).delete()
# for index, row in matches.iterrows():
# if pd.isna(row['ID']):
# continue
# id = row['ID']
# descr = row['Match description']
# home = row['Home team']
# away = row['Away team']
# date_format = '%d.%m.%Y %H:%M:%S'
# matchdate = datetime.datetime.strptime(row['Match date (GMT)'], date_format)
# competition_name = row['Name']
# rank = row['Rank']
# round = row['Round']
# facility = row['Facility']
# place = row['Facility place name']
# if pd.isna(rank):
# rank = 0
# if len(descr.split('-')) > 4:
# print("No team for ", descr)
# continue
# competition = Competition.objects.filter(name=competition_name, season=season).first()
# if not competition:
# competition = Competition.objects.create(name=competition_name, season=season, rank=rank)
# location = Location.objects.filter(name=facility, season=season).first()
# if not location:
# print("No location for ", facility)
# geocode_result = gmaps.geocode(f"{country}+{place}+{facility}")
# if len(geocode_result) > 0:
# lat = geocode_result[0]['geometry']['location']['lat']
# lng = geocode_result[0]['geometry']['location']['lng']
# location = Location.objects.create(name=facility,city=place,country=country, latitude=lat, longitude=lng, season=season, type=1)
# else:
# print("No geocode for ", facility)
# matchdescr = descr.split(':')[0][:-1].strip()
# homeTeam = Team.objects.filter(name=matchdescr.split('-')[0], season=season).first()
# if not homeTeam:
# homeTeam = Team.objects.create(name=matchdescr.split('-')[0],shortname=home, country=Country.objects.get(season=season,name='Wales'), location=location,latitude=location.latitude,longitude=location.longitude, season=season)
# awayTeam = Team.objects.filter(name=matchdescr.split('-')[1], season=season).first()
# if not awayTeam:
# awayTeam =Team.objects.create(name=matchdescr.split('-')[1],shortname=away, country=Country.objects.get(season=season,name='Wales'), season=season)
# day = Day.objects.filter(date=matchdate.date(), day=matchdate.strftime('%Y-%m-%d'), round=1, season=season).first()
# if not day:
# day = Day.objects.create(date=matchdate.date(), day=matchdate.strftime('%Y-%m-%d'), round=1, season=season)
# timeslot = TimeSlot.objects.filter(start=matchdate.time(), season=season).first()
# if not timeslot:
# timeslot = TimeSlot.objects.create(start=matchdate.time(), end=(matchdate+timedelta(hours=2)).time(), season=season, name=matchdate.time().strftime("%H%M"))
# roundObj = Round.objects.filter(name=round,number=round, season=season).first()
# if not roundObj:
# roundObj = Round.objects.create(name=round, number=round, season=season)
# roundObj.days.add(day)
# game = RefGame.objects.filter(location=location,round=round, homeTeam=homeTeam, awayTeam=awayTeam,scenario=scenario, competition=competition).first()
# if not game:
# RefGame.objects.create(location=location,round=round, homeTeam=homeTeam, awayTeam=awayTeam, day=day,timeslot=timeslot, scenario=scenario, competition=competition)
# seed_teams_and_games()
# # %%
# def seed_requirements():
# requirements = pd.read_excel('referees/fixtures/wales/v2/Competition Ranks.xlsx',skiprows=1)
# Requirement.objects.filter(season=season).delete()
# for index, row in requirements.iterrows():
# comp = row['Competition Name']
# rank = row['Competition Rank']
# ref = row['Referee']
# ref_cats = row['Category Required to Appoint As Ref']
# assistant1 = row['Assistant Referee 1']
# assistant2 = row['Assistant Referee 2']
# assistant_cats = row['Category Required to appoint as Assistant Referee']
# official = row['Fourth Official']
# official_cats = row['Category Required to Appoint as Fourth Official']
# max_dist = row['Maximum Distance for 1 Match Official to Travel (Miles)']
# try:
# max_dist = float(max_dist)
# except:
# max_dist = 0.0
# ref_categories = []
# if not pd.isna(ref_cats):
# ref_categories = [
# Category.objects.filter(name=cat, season=season).first() for cat in ref_cats.split(';')
# ]
# assistant_categories = []
# if not pd.isna(assistant_cats):
# assistant_categories = [
# Category.objects.filter(name=cat, season=season).first() for cat in assistant_cats.split(';')
# ]
# official_categories = []
# if not pd.isna(official_cats):
# official_categories = [
# Category.objects.filter(name=cat, season=season).first() for cat in official_cats.split(';')
# ]
# competition = Competition.objects.filter(name=comp, season=season).first()
# if competition:
# competition.rank = rank
# competition.save()
# if ref_categories:
# req = Requirement.objects.create(season=season, competition=competition, role=Role.objects.get(name='Referee', season=season), max_distance=max_dist)
# for cat in ref_categories:
# req.categories.add(cat)
# if assistant_categories:
# req1 = Requirement.objects.create(season=season, competition=competition, role=Role.objects.get(name='Assistant Referee 1', season=season), max_distance=max_dist)
# req2 = Requirement.objects.create(season=season, competition=competition, role=Role.objects.get(name='Assistant Referee 2', season=season), max_distance=max_dist)
# for cat in assistant_categories:
# req1.categories.add(cat)
# req2.categories.add(cat)
# if official_categories:
# req = Requirement.objects.create(season=season, competition=competition, role=Role.objects.get(name='Fourth Official', season=season), max_distance=max_dist)
# for cat in official_categories:
# req.categories.add(cat)
# seed_requirements()
# %%
availabilities = pd.read_excel('referees/fixtures/wales/Anonymised Referee Unavailability for Ligalytics.xlsx')
# %%
availabilities['Date from'] = pd.to_datetime(availabilities['Date from'], format='%d.%m.%Y', errors='coerce')
availabilities['Date to'] = pd.to_datetime(availabilities['Date to'], format='%d.%m.%Y', errors='coerce')
# %%
# %%
DelBlocking.objects.filter(season=season).delete()
for index, row in availabilities.iterrows():
start = row['Date from']
end = row['Date to']
dummy = row['Dummy ID']
if pd.isna(end):
end = start
if start >= datetime.datetime(2023,12,1) and end <= datetime.datetime(2024,1,1):
for i in range((end-start).days+1):
day = start + datetime.timedelta(days=i)
available = (row[day.weekday()+5] == 'X')
if not available:
delegate = Delegate.objects.filter(name=f"Person {dummy}", season=season).first()
dayObj = Day.objects.filter(day=day.strftime('%Y-%m-%d'), season=season).first()
if delegate and dayObj:
DelBlocking.objects.create(delegate=delegate, day=dayObj, season=season)
print(f"Blocked {delegate} on {dayObj}")
# %%

234
stats/scripts/script.py Normal file
View File

@ -0,0 +1,234 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
import django
django.setup()
from scheduler.models import *
from common.models import *
from common.stats.models import *
import csv
import datetime
# %%
# MOST ACTIVE
login_dict = defaultdict(lambda:0)
browsers = defaultdict(lambda:0)
devices = defaultdict(lambda:0)
with open('analyze_access.log', newline='') as csvfile:
reader = csv.reader(csvfile)
for row in reader:
date = datetime.datetime.strptime(row[0], '%Y-%m-%d %H:%M:%S')
splitstr = row[1].split('LOGGED IN:')
if len(splitstr) > 1:
kind = splitstr[0].split('INFO')[1].strip()
user = splitstr[1].split('from')[0].strip()
plattform = splitstr[1].split('with (')
if len(plattform) > 1:
plattform = plattform[1].split('/')[0].strip()
login_dict[(kind,user)] += 1
if 'Firefox' in row[1]:
browsers['Firefox'] += 1
if 'Chrome' in row[1]:
browsers['Chrome'] += 1
if 'Safari' in row[1]:
browsers['Safari'] += 1
if 'Edge' in row[1]:
browsers['Edge'] += 1
if 'Opera' in row[1]:
browsers['Opera'] += 1
if 'MSIE' in row[1]:
browsers['MSIE'] += 1
if 'Trident' in row[1]:
browsers['Trident'] += 1
if 'Netscape' in row[1]:
browsers['Netscape'] += 1
if 'Mozilla' in row[1]:
browsers['Mozilla'] += 1
if 'AppleWebKit' in row[1]:
browsers['AppleWebKit'] += 1
if 'Gecko' in row[1]:
browsers['Gecko'] += 1
if 'KHTML' in row[1]:
browsers['KHTML'] += 1
if 'iPhone' in row[1]:
devices['iPhone'] += 1
elif 'PC' in row[1]:
devices['PC'] += 1
elif 'K' in row[1]:
devices['Android'] += 1
elif 'Other' in row[1]:
devices['other'] += 1
browsers = sorted(browsers.items(), key=lambda x:x[1], reverse=True)[:10]
devices = sorted(devices.items(), key=lambda x:x[1], reverse=True)[:10]
# %%
login_dict = sorted(login_dict.items(), key=lambda x:x[1], reverse=True)
# %%
# Monday = 0
weekday_dict = defaultdict(lambda:[0,0,0,0,0,0,0])
weekday_ranking = [0,0,0,0,0,0,0]
hours_dict = defaultdict(lambda:[0]*24)
hours_ranking = [0]*24
clicks_per_day = defaultdict(lambda:defaultdict(lambda:0))
active_days = defaultdict(lambda:set())
active_hours = defaultdict(lambda:set())
wishes_added = defaultdict(lambda:0)
logouts = defaultdict(lambda:0)
solutions = defaultdict(lambda:0)
days = defaultdict(lambda:0)
deletions = defaultdict(lambda:0)
downloads = defaultdict(lambda:0)
actions = defaultdict(lambda:0)
active_teams = defaultdict(lambda:0)
active_clubs = defaultdict(lambda:0)
with open('analyze_info.log', newline='') as csvfile:
reader = csv.reader(csvfile)
for row in reader:
date = datetime.datetime.strptime(row[0], '%Y-%m-%d %H:%M:%S')
verbose = row[1].split('INFO')
if len(verbose) > 1:
user = verbose[1].split(':')[0].strip()
kind = verbose[1].split(':')[1].strip()
if user == 'md':
user = 'martin'
weekday_dict[user][date.weekday()] += 1
weekday_ranking[date.weekday()] += 1
hours_dict[user][date.hour] += 1
hours_ranking[date.hour] += 1
actions[user] += 1
clicks_per_day[user][date.strftime("%Y-%m-%d")] += 1
active_days[user].add(date.strftime("%Y-%m-%d"))
active_hours[user].add(date.strftime("%Y-%m-%d %H"))
if '/add/' in kind:
wishes_added[user] += 1
if kind == '/accounts/logout/':
logouts[user] += 1
if kind == '/schedule_sol/':
solutions[user] += 1
if 'day' in kind:
days[user] += 1
if 'delete' in kind:
deletions[user] += 1
if 'download' in kind:
downloads[user] += 1
if user == "SINGLETEAM":
active_teams[kind.split('/')[0].strip()] += 1
if user == "CLUB":
active_clubs[kind.split('/')[0].strip()] += 1
downloads = sorted(downloads.items(), key=lambda x:x[1], reverse=True)[:10]
wishes_added = sorted(wishes_added.items(), key=lambda x:x[1], reverse=True)[:10]
logouts = sorted(logouts.items(), key=lambda x:x[1], reverse=True)[:10]
solutions = sorted(solutions.items(), key=lambda x:x[1], reverse=True)[:10]
days = sorted(days.items(), key=lambda x:x[1], reverse=True)[:10]
deletions = sorted(deletions.items(), key=lambda x:x[1], reverse=True)[:10]
active_days = [(user,len(active_days[user])) for user in active_days]
active_days = sorted(active_days, key=lambda x:x[1], reverse=True)[:10]
active_hours = [(user,len(active_hours[user])) for user in active_hours]
active_hours = sorted(active_hours, key=lambda x:x[1], reverse=True)[:10]
actions = sorted(actions.items(), key=lambda x:x[1], reverse=True)[:10]
active_teams = sorted(active_teams.items(), key=lambda x:x[1], reverse=True)[:10]
active_clubs = sorted(active_clubs.items(), key=lambda x:x[1], reverse=True)[:10]
for user in clicks_per_day:
clicks_per_day[user] = sorted(clicks_per_day[user].items(), key=lambda x:x[1], reverse=True)
# %%
staff_user = ['martin','stephanwestphal','dirk','philipp','Kilian']
actions = {
u[0]:u[1] for u in actions
}
active = {
u[0]:u[1] for u in active_days
}
for user in staff_user:
print(user)
print(actions[user]//active[user])
# for s in staff_user:
# print(s)
# print(weekday_dict[s])
# print(hours_dict[s])
# print('')
# # %%
# commits_per_hour = "{&quot;0&quot;:15,&quot;1&quot;:9,&quot;2&quot;:5,&quot;3&quot;:6,&quot;4&quot;:3,&quot;5&quot;:1,&quot;6&quot;:22,&quot;7&quot;:28,&quot;8&quot;:63,&quot;9&quot;:111,&quot;10&quot;:161,&quot;11&quot;:194,&quot;12&quot;:160,&quot;13&quot;:141,&quot;14&quot;:145,&quot;15&quot;:150,&quot;16&quot;:145,&quot;17&quot;:131,&quot;18&quot;:85,&quot;19&quot;:93,&quot;20&quot;:110,&quot;21&quot;:112,&quot;22&quot;:76,&quot;23&quot;:34}"
# commits_per_weekday = "{&quot;Sunday&quot;:135,&quot;Monday&quot;:338,&quot;Tuesday&quot;:341,&quot;Wednesday&quot;:388,&quot;Thursday&quot;:388,&quot;Friday&quot;:302,&quot;Saturday&quot;:108}"
# commits_per_hour = json.loads(commits_per_hour.replace('&quot;','"'))
# commits_per_weekday = json.loads(commits_per_weekday.replace('&quot;','"'))
# %%
import json
with open('trello.json') as f:
data = json.load(f)
created = defaultdict(lambda:0)
for a in data['actions']:
if a['type'] == 'createCard':
created[a['memberCreator']['fullName']] += 1
# %%
# MOST SCENARIOS
scenarios = {}
for league in League.objects.all():
scenarios[league.name] = Scenario.objects.filter(season__league=league,lastComputation__gte=datetime.datetime(2023,1,1)).count()
scenarios = sorted(scenarios.items(), key=lambda x:x[1], reverse=True)
# %%
# MOST WISHES
wishes = {}
for league in League.objects.all():
for scenario in Scenario.objects.filter(season__league=league,lastComputation__gte=datetime.datetime(2023,1,1)):
wishes[league.name] = HAWish.objects.filter(scenario=scenario).count()+EncWish.objects.filter(scenario=scenario).count()+Blocking.objects.filter(scenario=scenario).count()+Pairing.objects.filter(scenario=scenario).count()
wishes = sorted(wishes.items(), key=lambda x:x[1], reverse=True)[:10]
# %%

200
uefa/scripts/afc_chl23_seeder.py Executable file
View File

@ -0,0 +1,200 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
# settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
# settings.DATABASES['default']['HOST'] = '0.0.0.0'
# settings.DATABASES['default']['PORT'] = '5432'
# settings.DATABASES['default']['USER'] = 'postgres'
# settings.DATABASES['default']['PASSWORD'] = 'secret123'
# settings.DATABASES['default']['NAME'] = 'mypgsqldb'
# settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
# settings.DATABASES['default']['AUTOCOMMIT'] = True
# settings.DATABASES['default']['CONN_MAX_AGE'] = 0
# settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
# settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from django.shortcuts import HttpResponseRedirect
from django.http import HttpResponse, JsonResponse
from django.utils import timezone
from django.urls import reverse
from django.core.files.storage import FileSystemStorage
from django.core.mail import send_mail
from django_tex.shortcuts import render_to_pdf
from celery.result import AsyncResult
import googlemaps
import timeit
import random
import json
import builtins as __builtin__
import csv
from leagues.celery import celery
from leagues.settings import EMAIL_DEFAULT_FROM, EMAIL_DEFAULT_TO
from leagues.settings import RUN_ENV, INSTANCE, DEBUG
from common.tasks import log_telegram
from common.functions import *
from scheduler.models import *
from scheduler.helpers import *
from scheduler.widgets import widget_context_kpis
from scheduler.solver.optimizer import optimize_2phases, optimize_sequentially
import scheduler.solver.optimizer as so
from draws.solver import optimize_draws
import time as timer
from qualifiers.helpers import import_globals
gmaps = googlemaps.Client(
key='AIzaSyB76EhR4OqjdXHQUiTkHZC0Svx_7cPGqyU')
# %%
scenario = Scenario.objects.get(id=10)
# import_globals(scenario.season.id)
# teams = scenario.season.scheduler_teams.all()
# %%
new_teams = []
new_teams.append(("Group A", "Paxtakor Taschkent, Uzbekistan (UZB)",))
new_teams.append(("Group A", "al-Fayha FC, Saudi Arabia (KSA)",))
new_teams.append(("Group A", "Ahal FK, Turkmenistan (TKM)",))
new_teams.append(("Group A", "al Ain Club, United Arab Emirates (UAE)",))
new_teams.append(("Group B", "al-Sadd SC, Qatar (QAT)",))
new_teams.append(("Group B", "Nasaf Karschi, Uzbekistan (UZB)",))
new_teams.append(("Group B", "al-Faisaly, Jordan (JOR)",))
new_teams.append(("Group B", "Sharjah FC, United Arab Emirates (UAE)",))
new_teams.append(("Group C", "Ittihad FC, Saudi Arabia (KSA)",))
new_teams.append(("Group C", "Sepahan FC, Iran (IRN)",))
new_teams.append(("Group C", "al-Quwa al-Dschawiya, Iraq (IRQ)",))
new_teams.append(("Group C", "AGMK FC, Uzbekistan (UZB)",))
new_teams.append(("Group D", "al-Hilal, Saudi Arabia (KSA)",))
new_teams.append(("Group D", "Nassaji Mazandaran, Iran (IRN)",))
new_teams.append(("Group D", "Mumbai City FC, India (IND)",))
new_teams.append(("Group D", "Navbahor Namangan, Uzbekistan (UZB)",))
new_teams.append(("Group E", "Persepolis Teheran, Iran (IRN)",))
new_teams.append(("Group E", "al-Duhail SC, Qatar (QAT)",))
new_teams.append(("Group E", "FC Istiklol, Tajikistan (TJK)",))
new_teams.append(("Group E", "al-Nassr FC, Saudi Arabia (KSA)",))
new_teams.append(("Group F", "Jeonbuk Hyundai Motors, South Korea (KOR)",))
new_teams.append(("Group F", "Bangkok United, Thailand (THA)",))
new_teams.append(("Group F", "Lion City Sailors, Singapore (SGP)",))
new_teams.append(("Group F", "Kitchee SC, Hong Kong (HKG)",))
new_teams.append(("Group G", "Yokohama F. Marinos, Japan (JPN)",))
new_teams.append(("Group G", "Shandong Taishan, China (CHN)",))
new_teams.append(("Group G", "Kaya FC-Iloilo, Philippines (PHI)",))
new_teams.append(("Group G", "Incheon United, South Korea (KOR)",))
new_teams.append(("Group H", "Buriram United, Thailand (THA)",))
new_teams.append(("Group H", "Ventforet Kofu, Japan (JPN)",))
new_teams.append(("Group H", "Melbourne City FC, Australia (AUS)",))
new_teams.append(("Group H", "Zhejiang Professional FC, China (CHN)",))
new_teams.append(("Group I", "Ulsan Hyundai, South Korea (KOR)",))
new_teams.append(("Group I", "Kawasaki Frontale, Japan (JPN)",))
new_teams.append(("Group I", "Johor Darul Tazim FC, Malaysia (MAS)",))
new_teams.append(("Group I", "BG Pathum United FC, Thailand (THA)",))
new_teams.append(("Group J", "Wuhan Three Towns FC, China (CHN)",))
new_teams.append(("Group J", "Pohang Steelers, South Korea (KOR)",))
new_teams.append(("Group J", "Hà Nội FC, Vietnam (VIE)",))
new_teams.append(("Group J", "Urawa Red Diamonds, Japan (JPN)",))
# %%
pot_converter = {
"A": 1,
"B": 2,
"C": 3,
"D": 4,
"E": 5,
"F": 6,
"G": 7,
"H": 8,
"I": 9,
"J": 10,
}
Conference.objects.filter(scenario=scenario).delete()
for g in pot_converter.keys():
Conference.objects.create(scenario=scenario, name=f"Group {g}", display_group=True, collapseInView=False)
Conference.objects.create(scenario=scenario, name='West', collapseInView=True, display_group=False)
Conference.objects.create(scenario=scenario, name='East', collapseInView=True, display_group=False)
pot = 1
for i,t in enumerate(new_teams):
group = t[0]
team_name = t[1].split(",")[0]
team_country = t[1].split(",")[1].split("(")[0].strip()
team_country_code = t[1].split(",")[1].split("(")[1].split(")")[0].strip()
teamObj = Team.objects.filter(name=team_name, season=scenario.season).first()
if not teamObj:
gcountry = GlobalCountry.objects.filter(uefa=team_country_code)
if not gcountry:
gcountry = GlobalCountry.objects.filter(alpha3=team_country_code)
if not gcountry:
print("\t", "NOT FOUND")
geocode_result = gmaps.geocode(team_name+" "+team_country)
if len(geocode_result) > 0:
location = geocode_result[0]['geometry']['location']
print("\t", location)
else:
location = {'lat': 0, 'lng': 0}
print("\t", "NOT FOUND")
teamObj = Team.objects.create(
name=team_name,
country=team_country_code,
season=scenario.season,
active=True,
latitude=location['lat'],
longitude=location['lng'],
)
teamObj.shortname = teamObj.name[:5]
teamObj.position = i+1
teamObj.pot = pot
teamObj.save()
pot += 1
if pot > 4:
pot = 1
Conference.objects.get(scenario=scenario, name=group).teams.add(teamObj)
if pot_converter[group.split(" ")[1]] <= 5:
Conference.objects.get(scenario=scenario, name="West").teams.add(teamObj)
else:
Conference.objects.get(scenario=scenario, name="East").teams.add(teamObj)
# %%

54
uefa/scripts/django_script.py Executable file
View File

@ -0,0 +1,54 @@
# %%
# Wichtiger Header + Xpress
"""
##############################################################################################################
"""
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
"""
##############################################################################################################
"""
# %%
# Ab hier dann der eigene Code
from scheduler.models import *
scenario = Scenario.objects.first()
print(scenario.name)
# %%

View File

@ -0,0 +1,174 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.tasks.optimize import optimize
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from datetime import timedelta
# %%
from django.contrib.sessions.models import Session
scenario = Scenario.objects.get(id=8506)
season = scenario.season
days = Day.objects.filter(season=scenario.season)
teams = Team.objects.filter(season=scenario.season)
federation = FederationMember.objects.filter(season=scenario.season).first().federation
stadiums = Stadium.objects.filter(federation=federation)
stadiumtimeslotblockings = StadiumTimeSlotBlocking.objects.filter(stadiumTimeSlot__stadium__in=stadiums)
# %%
getTeamByName = {}
for t in teams:
if t.name == "AHOUD Devils Nijmegen U9":
name = "Nijmegen Devils"
elif t.name == "Unis Flyers Heerenveen U7/U9/U11":
name="UNIS Flyers Heerenveen"
elif t.name == "IJCU Utrecht U9/U11":
name="Utrecht Dragons"
else:
name = t.name.split("U7")[0].split("U9")[0].split("U11")[0].strip()
getTeamByName[name] = t
getStadiumByName = {}
for s in stadiums:
if s.name == "IJssportcentrum Eindhoven (kleine hal)":
name = "IJssportcentrum Eindhoven (Kleine hal)"
elif s.name == "Sportiom":
name = "Den Bosch"
else:
name = s.name
getStadiumByName[name] = s
# %%
stsb = []
with open('LOS-ScheduleImportTemplate_EN-U9.csv', newline='') as csvfile:
reader = csv.reader(csvfile)
next(reader, None)
next(reader, None)
for row in reader:
# print(row)
raw_dayobj = datetime.datetime.strptime(row[3],'%m/%d/%Y')
raw_time = row[4]
raw_stadium= row[7]
raw_team1 = row[8].split("U9")[0].strip()
raw_team2 = row[9].split("U9")[0].strip()
# day
day = days.filter(day=raw_dayobj.strftime('%Y-%m-%d')).first()
if not day:
print("\tERROR",day)
break
# teams
team1 = getTeamByName.get(raw_team1, None)
team2 = getTeamByName.get(raw_team2,None)
if not team1 or not team2:
print("\tERROR",team1,team2)
break
# stadium
stadium = None
for s in getStadiumByName.keys():
if raw_stadium in s:
stadium = getStadiumByName[s]
break
if not stadium:
print("\tERROR",stadium)
break
# timeslot
weekday = raw_dayobj.strftime('%A')+"s"
start = datetime.time(int(raw_time.split(":")[0]),int(raw_time.split(":")[1]))
end = datetime.time(int(raw_time.split(":")[0])+2 % 24,int(raw_time.split(":")[1]))
timeslot = StadiumTimeSlot.objects.filter(stadium=stadium,weekday=weekday,start=start,end=end)
if timeslot.count() > 1:
print("ERROR",stadium,weekday,start,end)
break
else:
timeslot = timeslot.first()
if not timeslot:
club = StadiumTimeSlot.objects.filter(stadium=stadium).first().club
print("Missing",stadium,weekday,start,end)
timeslot = StadiumTimeSlot.objects.create(
stadium=stadium,
club=club,
weekday=weekday,
start=start,
end=end
)
stsb.append(StadiumTimeSlotBlocking(stadiumTimeSlot = timeslot,
homeTeam = team1,
awayTeam = team2,
day = day.day,
)
)
StadiumTimeSlotBlocking.objects.bulk_create(stsb)
# %%

214
uefa/scripts/script copy.py Executable file
View File

@ -0,0 +1,214 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
# settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
# settings.DATABASES['default']['HOST'] = '0.0.0.0'
# settings.DATABASES['default']['PORT'] = '5432'
# settings.DATABASES['default']['USER'] = 'postgres'
# settings.DATABASES['default']['PASSWORD'] = 'secret123'
# settings.DATABASES['default']['NAME'] = 'mypgsqldb'
# settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
# settings.DATABASES['default']['AUTOCOMMIT'] = True
# settings.DATABASES['default']['CONN_MAX_AGE'] = 0
# settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
# settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD, XPRESS_PY
import xpress as xp
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from common.functions import getRandomHexColor
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.tasks.optimize import optimize
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from datetime import timedelta
# %%
# import requests
# data = json.loads(b'{\r\n "season": "UCL 24/25",\r\n "team": 52277,\r\n "pots": [1,2,3,4],\r\n "games":[[50051, 52747], [50138, 50051], [50051, 50147]]\r\n}')
# headers = {'Content-type': 'application/json', 'Authorization': 'R6v1e9Q5W8aS3b7C4x2KpZqL9yFmXnDz'}
# requests.post('http://localhost:8000/draws/checker/',json=data, headers=headers)
# %%
# # scenario.sol_solution
scenario = Scenario.objects.get(id=1)
"""GUROBI"""
scenario_id = scenario.id
fixed_games = []
print("\n")
ttt = time.time()
tt = time.time()
scenario = Scenario.objects.get(id=scenario_id)
teamObjects = Team.objects.filter(season=scenario.season,active=True).exclude(name='-').values()
teams = [t['id'] for t in teamObjects]
t_pot = {t['id'] : t['pot'] for t in teamObjects}
t_name = {t['id'] : t['name'] for t in teamObjects}
t_country = {t['id'] : t['countryObj_id'] for t in teamObjects if t['countryObj_id'] }
t_master = {t['id'] : None for t in teamObjects}
pots = sorted(list(set(t_pot.values())))
p_teams = { p:[t for t in teams if t_pot[t]==p] for p in pots }
countries = [c.id for c in scenario.season.countries.all()]
teams_from_country = { c:[t for t in teams if t_country[t]==c] for c in countries }
# print ("CHECKING", len(fixed_games) , "games!")
drawFound = False
for draw in Draw.objects.filter(season=scenario.season, active=True ):
drawFound = True
# print ("DRAW ",draw)
supergroups = []
sg_teams = {}
sg_groups = {}
sg_pots = {}
sg_games_per_team = {}
sg_games_against_pot = {}
for sg in SuperGroup.objects.filter(draw = draw):
supergroups.append(sg.id)
# sg_teams[sg.id] = [ t.id for t in sg.teams.all()]
# sg_groups[sg.id] = [ t.id for t in sg.groups.all()]
sg_teams[sg.id] = sg.teams.values_list('id',flat=True)
sg_groups[sg.id] = sg.groups.values_list('id',flat=True)
maxpot = max([ t_pot[t] for t in sg_teams[sg.id]])
sg_pots[sg.id]=range(1, maxpot+1)
sg_games_per_team[sg.id]= sg.gamesPerTeam
sg_games_against_pot[sg.id]= sg_games_per_team[sg.id]/maxpot
for t in sg_teams[sg.id]:
t_master[t]=sg.id
possible_opponents = { (t,p): [t2 for t2 in sg_teams[sg.id] if t_country[t2]!=t_country[t] and t_pot[t2]==p] for t in sg_teams[sg.id] for p in pots}
print("\t1",time.time()-tt)
tt = time.time()
model = xp.problem(name='Draws', sense=xp.minimize)
model.setControl ('outputlog', 0)
x = {}
gameVarExists= { (t1,t2): False for t1 in teams for t2 in teams}
for sg in supergroups:
for t1 in sg_teams[sg]:
for t2 in sg_teams[sg]:
if t_country[t1] != t_country[t2]:
# x[t1, t2] = pulp.LpVariable('x_'+str(t1)+'_'+str(t2),lowBound=0, upBound=1, cat=pulp.LpInteger)
x[t1, t2] = xp.var(ub=1, vartype=xp.integer)
gameVarExists[(t1,t2)]=True
model.addVariable(x)
# REQUIREMENTS
for t in sg_teams[sg]:
for p in sg_pots[sg]:
if sg_games_against_pot[sg]==2:
model.addConstraint(xp.Sum(x[t,t2] for t2 in p_teams[p] if gameVarExists[(t,t2)]) == 1)
model.addConstraint(xp.Sum(x[t2,t] for t2 in p_teams[p] if gameVarExists[(t2,t)]) == 1)
else:
model.addConstraint(xp.Sum(x[t,t2] for t2 in p_teams[p] if gameVarExists[(t,t2)]) <= 1)
model.addConstraint(xp.Sum(x[t2,t] for t2 in p_teams[p] if gameVarExists[(t2,t)]) <= 1)
model.addConstraint(xp.Sum(x[t2,t] + x[t,t2] for t2 in p_teams[p] if gameVarExists[(t,t2)]) == sg_games_against_pot[sg])
if p%2==0:
# exactly one home game against pots 1,2, one against pot 3,4 one against pots 5,6
model.addConstraint(xp.Sum(x[t,t2] for t2 in p_teams[p-1]+p_teams[p] if gameVarExists[(t,t2)]) == 1)
for c in countries:
if c != t_country[t]:
tcnt = [t2 for t2 in teams_from_country[c] if t_master[t]==t_master[t2]]
if len(tcnt)>draw.max_opponents_from_same_country:
model.addConstraint(xp.Sum(x[t,t2]+x[t2,t] for t2 in teams_from_country[c] if t_master[t]==t_master[t2] and gameVarExists[(t,t2)]) <= draw.max_opponents_from_same_country)
print("\t2",time.time()-tt)
tt = time.time()
for cl in draw.clashes.filter(type="Game").prefetch_related('countries','teams'):
# cl_countries = [ c.id for c in cl.countries.all() ]
cl_countries = cl.countries.values_list('id',flat=True)
cl_teams = list(cl.teams.values_list('id',flat=True)) + [ t for t in teams if t_country[t] in cl_countries ]
cl_teams = list(set(cl_teams))
# print("CLASH" ,cl, cl_countries , cl_teams , [ (t_name[t] , t_country[t]) for t in cl_teams ] )
if cl.minTeams>0:
model.addConstraint(xp.Sum(x[t1,t2] for t1 in cl_teams for t2 in cl_teams if gameVarExists[(t1,t2)]) >= cl.minTeams)
# print ("min implemented")
if len(cl_teams)>1:
model.addConstraint(xp.Sum(x[t1,t2] for t1 in cl_teams for t2 in cl_teams if gameVarExists[(t1,t2)]) <= cl.maxTeams)
# print ("max implemented")
print("\t3",time.time()-tt)
# FIXATIONS
for (t1,t2) in fixed_games:
if gameVarExists[(t1,t2)]:
model += x[t1,t2] == 1
else:
print ("GAME DOES NOT EXIST!!")
print( False)
print("\t3",time.time()-tt)
# for (t1,t2) in [(t1,t2) for (t1,t2) in x.keys() if t1 < t2]:
for (t1,t2) in [(t1,t2) for (t1,t2) in x.keys() if t1 < t2]:
model.addConstraint(x[t1,t2] + x[t2,t1] <= 1)
# model.addConstraint(x[t1,t2] + x[t2,t1] <= 1)
print("\t4",time.time()-tt)
# model.solve(XPRESS(msg=0,timeLimit=120,keepFiles=0))
tt = time.time()
# model.solve(XPRESS_PY(msg=0,timeLimit=120))
model.solve()
# model.solve(GUROBI(msg=0,timeLimit=120))
# model.solve(PULP_CBC_CMD(timeLimit = 120, threads = 8,msg=0))
print("\t5",time.time()-tt)
print("TIME",time.time()-ttt)

301
uefa/scripts/script.py Executable file
View File

@ -0,0 +1,301 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from common.functions import getRandomHexColor
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.tasks.optimize import optimize
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from datetime import timedelta
# %%
import requests
data = json.loads(b'{\r\n "season": "UCL 24/25",\r\n "team": 52277,\r\n "pots": [1,2,3,4],\r\n "games":[[50051, 52747], [50138, 50051], [50051, 50147]]\r\n}')
headers = {'Content-type': 'application/json', 'Authorization': 'R6v1e9Q5W8aS3b7C4x2KpZqL9yFmXnDz'}
requests.post('http://localhost:8000/draws/checker/',json=data, headers=headers)
# %%
# %%
scenario = Scenario.objects.get(id=9340)
scenario.sol_solution
# %%
season = scenario.season
all_rounds = []
getDateByIso = {}
season = scenario.season
teams = Team.objects.filter(season=scenario.season,active=True)
higherHomeGames = defaultdict(lambda: [])
higherAwayGames = defaultdict(lambda: [])
higherDates = scenario.season.higherDates()
for game in scenario.season.higherGames():
higherHomeGames[game[1]].append(game)
higherAwayGames[game[2]].append(game)
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
all_rounds.append(higherRound)
getDateByIso[higherRound] = higherDates[game[0]]
higherTeams = set(list(higherHomeGames.keys()) + list(higherAwayGames.keys()))
gameRequirements = GameRequirement.objects.filter(scenario=scenario)
# stadium_clashes = Pairing.objects.filter(scenario=scenario,type="Home",prio="Hard",active=True,team2__in=teams)
pairings = Pairing.objects.filter(scenario=scenario,active=True,team2__in=teams,prio__in=['Hard','A'])
pairings_dependencies = Pairing.objects.filter(scenario=scenario,active=True,team2__in=higherTeams,prio__in=['Hard','A'])
days = Day.objects.filter(season=scenario.season, maxGames__gt=0)
blockings = Blocking.objects.filter(scenario=scenario)
seedgames = EncWish.objects.filter(scenario=scenario,active=True,reason__contains='SEED')
encwishes = EncWish.objects.filter(scenario=scenario,active=True,prio__in=['Hard','A'],timeframe=1,forOneDay=False,forOneDayNum=1)
hawishes = HAWish.objects.filter(scenario=scenario,active=True,prio__in=['Hard','A'],forEachDay=False,forOneDay=False)
uclpatterns = SpecialWish.objects.filter(scenario=scenario,name='UCL24Patterns',active=True).exists()
alternatestart = SpecialWish.objects.filter(scenario=scenario,name='AlternateStart',active=True).exists()
maxTourLength = season.maxTourLength
groups = Conference.objects.filter(scenario=scenario).filter(name__in=["UEL","UECL"])
uel_teams = list(groups.filter(name="UEL").first().teams.order_by('pot','country').values_list('id',flat=True))
uecl_teams = list(groups.filter(name="UECL").first().teams.order_by('pot','country').values_list('id',flat=True))
prioVal ={'A': 25 , 'B': 5 , 'C': 1, 'Hard' : 1000}
pairings_prio = {
(p.team1.id,p.team2.id):prioVal[p.prio] for p in pairings
}
encwish_prio = {
p.id:prioVal[p.prio] for p in encwishes
}
hawish_prio = {
p.id:prioVal[p.prio] for p in hawishes
}
dependency_prio = {
(p.team1.id,p.team2.id):prioVal[p.prio] for p in pairings_dependencies
}
daysPerRound = defaultdict(lambda:[])
# getRoundByDay = {}
# for d in days:
# daysPerRound[d.round].append(d)
# getRoundByDay[d.id] = d.round
getRoundByIso = {}
getIsoByRound = {}
getDateByDay = {}
for d in days:
getDateByDay[d] = datetime.datetime.strptime(d.day,"%Y-%m-%d")
iso = datetime.datetime.strptime(d.day,"%Y-%m-%d").isocalendar()
getRoundByIso[f"{iso.year}-{iso.week}"] = d.round
getIsoByRound[d.round] = f"{iso.year}-{iso.week}"
all_rounds.append(f"{iso.year}-{iso.week}")
getDateByIso[f"{iso.year}-{iso.week}"] = getDateByDay[d]
daysPerRound[f"{iso.year}-{iso.week}"].append(d)
all_rounds = sorted(list(set(all_rounds)))
single_day_rounds = [r for r in daysPerRound if len(daysPerRound[r]) == 1]
two_day_rounds = [r for r in daysPerRound if len(daysPerRound[r]) == 2 ]
multi_day_rounds = [r for r in daysPerRound if len(daysPerRound[r]) >= 3 ]
team_ids = list(teams.values_list('id',flat=True))
getTeamByID = {
t.id:t for t in teams
}
# list all rounds where each day is blocked for a team
blockedRounds = {(t.id,r):True for r in all_rounds for t in teams}
for t in teams:
tblocks = blockings.filter(team=t)
for r in all_rounds:
for d in daysPerRound[r]:
if not tblocks.filter(day=d).exists():
blockedRounds[(t.id,r)] = False
break
gamereqs = []
opponents_from_pot = defaultdict(lambda:defaultdict(lambda:[]))
for req in gameRequirements:
gamereqs.append((req.team1.id,req.team2.id))
opponents_from_pot[req.team1.id][req.team2.pot].append(req.team2.id)
opponents_from_pot[req.team2.id][req.team1.pot].append(req.team1.id)
pot = {}
teams_in_pot = {}
for i in teams.values_list('pot',flat=True).distinct():
pot[i] = teams.filter(pot=i)
teams_in_pot[i] = list(teams.filter(pot=i).values_list('id',flat=True))
topTeams = teams.filter(attractivity__gte=4)
topGames = [(t1.id,t2.id) for t1 in topTeams for t2 in topTeams if (t1.id,t2.id) in gamereqs]
topTeam_clashes = {t.id:[] for t in topTeams}
# for t in topTeams:
# for pair in stadium_clashes.filter(team1=t):
# topTeam_clashes[t.id].append(pair.team2.id)
# for pair in stadium_clashes.filter(team2=t):
# topTeam_clashes[t.id].append(pair.team1.id)
rounds = all_rounds
# ucl_rounds = [r for i,r in enumerate(rounds) if i in [0,2,3,4,5,6,8,9]]
uel_rounds = [r for i,r in enumerate(rounds) if i in [1,2,3,4,5,6,8,9]]
uecl_rounds = [r for i,r in enumerate(rounds) if i in [2,3,4,5,6,7]]
# BASICWISHES
# for e in hawishes.order_by('prio'):
# if e.timeslots.count() > 0:
# continue
# elemTeams = [[t] for t in e.get_teams()] if e.forEachTeam else [e.get_teams()]
# elemRounds = [set([f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}" for d in e.get_days()])]
# if e.minGames > 0:
# for teamset in elemTeams:
# for roundset in elemRounds:
# if e.homeAway == "Home":
# print("ADDED HA MIN",e.id,e.prio,e.homeAway,e.reason,teamset,roundset,e.minGames)
# elif e.homeAway == "Away":
# print("ADDED HA MIN",e.id,e.prio,e.homeAway,e.reason,teamset,roundset,e.minGames)
# else:
# print("ADDED HA MIN",e.id,e.prio,e.homeAway,e.reason,teamset,roundset,e.minGames)
# if e.maxGames >= 0:
# for teamset in elemTeams:
# for roundset in elemRounds:
# if e.homeAway == "Home":
# print("ADDED HA MAX",e.id,e.prio,e.homeAway,e.reason,teamset,roundset,e.maxGames)
# elif e.homeAway == "Away":
# print("ADDED HA MAX",e.id,e.prio,e.homeAway,e.reason,teamset,roundset,e.maxGames)
# else:
# print("ADDED HA MAX",e.id,e.prio,e.homeAway,e.reason,teamset,roundset,e.maxGames)
for e in encwishes.filter(id=134891).order_by('prio'):
if e.timeslots.count() > 0:
continue
elemTeams1 = [[t] for t in e.get_teams1()] if e.forEachTeam1 else [e.get_teams1()]
elemTeams2 = [[t] for t in e.get_teams2()] if e.forEachTeam2 else [e.get_teams2()]
if all(t.id in uel_teams for t in e.get_teams1()):
elemRounds = [[f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}"] for d in e.get_days() if f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}" in uel_rounds] if e.forEachDay else \
[set([f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}" for d in e.get_days() if f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}" in uel_rounds])]
elif all(t.id in uecl_teams for t in e.get_teams1()):
elemRounds = [[f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}"] for d in e.get_days() if f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}" in uecl_rounds] if e.forEachDay else \
[set([f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}" for d in e.get_days() if f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}" in uecl_rounds])]
else:
elemRounds = [[f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}"] for d in e.get_days()] if e.forEachDay else \
[set([f"{d.date.isocalendar()[0]}-{d.date.isocalendar()[1]}" for d in e.get_days()])]
if e.minGames > 0:
if e.useEncounterGroups:
for i,roundset in enumerate(elemRounds):
encounters = Encounter.objects.filter(encounterGroup__in=e.encounterGroups.all())
if e.symmetry:
print("ADDED ENC (SYMMETRY) MIN",e.id,e.prio,e.reason,[(t1,t2) for enc in encounters for t1 in enc.homeTeams.all() for t2 in enc.awayTeams.all()],roundset,e.minGames,e.symmetry,i)
else:
print("ADDED ENC MIN",e.id,e.prio,e.reason,[(t1,t2) for enc in encounters for t1 in enc.homeTeams.all() for t2 in enc.awayTeams.all()],roundset,e.minGames,e.symmetry,i)
else:
for teamset1 in elemTeams1:
for teamset2 in elemTeams2:
for i,roundset in enumerate(elemRounds):
print(roundset)
print(teamset1)
print(teamset2)
if e.symmetry:
print("\tADDED ENC (SYMMETRY) MIN",e.id,e.prio,e.reason,teamset1,teamset2,roundset,e.minGames,e.symmetry,i)
else:
print("\tADDED ENC MIN",e.id,e.prio,e.reason,teamset1,teamset2,roundset,e.minGames,e.symmetry,i)
if e.maxGames >= 0:
if e.useEncounterGroups:
for i,roundset in enumerate(elemRounds):
print(roundset)
encounters = Encounter.objects.filter(encounterGroup__in=e.encounterGroups.all())
for enc in encounters:
print(enc)
if e.symmetry:
print("\tADDED ENC (SYMMETRY) MAX",e.id,e.prio,e.reason,[(t1,t2) for enc in encounters for t1 in enc.homeTeams.all() for t2 in enc.awayTeams.all()],roundset,e.maxGames,e.symmetry,i)
else:
print("\tADDED ENC MAX",e.id,e.prio,e.reason,[(t1,t2) for enc in encounters for t1 in enc.homeTeams.all() for t2 in enc.awayTeams.all()],roundset,e.maxGames,e.symmetry,i)
else:
for teamset1 in elemTeams1:
for teamset2 in elemTeams2:
for i,roundset in enumerate(elemRounds):
print(roundset)
print(teamset1)
print(teamset2)
if e.symmetry:
print("\tADDED ENC (SYMMETRY) MAX",e.id,e.prio,e.reason,teamset1,teamset2,roundset,e.maxGames,e.symmetry,i)
else:
print("\tADDED ENC MAX",e.id,e.prio,e.reason,teamset1,teamset2,roundset,e.maxGames,e.symmetry,i)
# %%

173
uefa/scripts/solve_uefa24.py Executable file
View File

@ -0,0 +1,173 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.tasks.optimize import optimize
from scheduler.solver.tasks.optimize_submodels import ueluecl24_basicmodell_v2
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from datetime import timedelta
from django.contrib.sessions.models import Session
scenario = Scenario.objects.get(id=9051)
# scenario = Scenario.objects.get(id=9368)
# scenario = Scenario.objects.get(id=1)
season = scenario.season
s2 = scenario.id
user_name = 'md'
user_is_staff = True
runMode = 'New'
localsearch_time = 0
RUN_ENV = 'local'
SOLVER = 'xpress'
# Conference.objects.filter(scenario=scenario,name__in=["UEL","UECL"]).update(reopt=True)
sol = optimize(task=None, s2=s2, user_name=user_name, user_is_staff=user_is_staff,
runMode=runMode, localsearch_time=localsearch_time, RUN_ENV=RUN_ENV, solver=SOLVER)
# ueluecl24_basicmodell_v2(SOLVER,scenario,[],[],maxTime=3600)
# %%
# hawishes = HAWish.objects.filter(scenario=scenario)
# # elemHaWishes ={e['id'] : [] for e in hawishes}
# # elemHaWishTeams={}
# # elemHaWishDays ={}
# # elemHaWishFirstDay ={}
# # elemHaWishNum ={}
# cntr =1
# for e in hawishes:
# elemTeams = [[t] for t in e.get_teams()] if e.forEachTeam else [e.get_teams()]
# elemRounds = [[d] for d in e.get_rounds()] if e.forEachDay else [e.get_rounds()]
# if e.homeAway == "HOME":
# if e.minGames > 0:
# for teamset in elemTeams:
# for roundset in elemRounds:
# model += lpSum([x[r,t.id,t2.id] for t in teamset for r in roundset for t2 in teams if (r,t.id,t2.id) in x.keys()]) >= e.minGames - seedViolation[seed.id]
# # elemHaWishes[e['id']]=[]
# # allElemDays=[]
# # thisDaySet=[]
# # lastDaySet = []
# # # print("elemDays",elemDays)
# # for d in elemDays :
# # # print (e)
# # if (e['forEachDay'] or e['forOneDay']) and e['timeframe']!=1:
# # thisDaySet=[]
# # # day1= parse(getDayById[d[0]]['day'])
# # day1= getDateTimeDay[d[0]]
# # if e['timeframe']>1:
# # day2=day1 + datetime.timedelta(days=e['timeframe']-1)
# # for d3 in days:
# # # dt = parse(getDayById[d3]['day'])
# # dt= getDateTimeDay[d3]
# # if day1<=dt and dt<=day2 :
# # thisDaySet.append(d3)
# # else:
# # r1 = getDayById[d[0]]['round']
# # for d3 in days:
# # dt= getDateTimeDay[d3]
# # # dt = parse(getDayById[d3]['day'])
# # if day1<=dt and r1 <= getRoundByDay[d3] and getRoundByDay[d3]< r1 + (-e['timeframe']) :
# # thisDaySet.append(d3)
# # # print (" ROUND HA WISH ", e['reason'], thisDaySet, e['timeframe'])
# # else:
# # thisDaySet=d
# # # only create wish id new day set is superset
# # if len([d for d in thisDaySet if d not in lastDaySet])>0:
# # for t in elemTeams:
# # cntr+=1
# # elemHaWishes[e['id']].append(cntr)
# # elemHaWishTeams[cntr]=t
# # elemHaWishDays[cntr]=thisDaySet.copy()
# # elemHaWishFirstDay[cntr]=d[0]
# # elemHaWishNum[cntr]=1
# # if e['maxGames'] ==0:
# # elemHaWishNum[cntr]=len(elemHaWishDays[cntr])*len(elemHaWishTeams[cntr])
# # if e['minGames'] > 0:
# # elemHaWishNum[cntr]=e['minGames']
# # lastDaySet = thisDaySet.copy()
# # allElemDays+= thisDaySet
# # hawRounds[e['id']]=[]
# # for d3 in set(allElemDays):
# # hawRounds[e['id']]+=getRoundsByDay[d3]
# # hawRounds[e['id']]=sorted(list(set(hawRounds[e['id']])))
# # hawRoundsString[e['id']]= ""
# # for r in hawRounds[e['id']]:
# # hawRoundsString[e['id']]+= str(r)+"_"
# # if hawRoundsString[e['id']]!="":
# # hawRoundsString[e['id']]=hawRoundsString[e['id']][:-1]
# # e['nWishes'] = sum ( elemHaWishNum[ee] for ee in elemHaWishes[e['id']] )
# # if e['forOneDay']:
# # e['nWishes'] = e['forOneDayNum'] * len(elemTeams)
# # nElemHaWishes= sum(w['nWishes'] for w in hawishes)
# # %%

View File

@ -0,0 +1,280 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
from pulp import *
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from django.contrib.sessions.models import Session
scenario = Scenario.objects.get(id=9360)
from scheduler.solver.tasks.optimize import optimize
s2 = scenario.id
user_name = 'md'
user_is_staff = True
runMode = 'Improve'
localsearch_time = 60
RUN_ENV = 'local'
SOLVER = 'xpress'
teams = Team.objects.filter(season=scenario.season,active=True,conference__name="UECL").distinct()
gamereqs = GameRequirement.objects.filter(scenario=scenario)
# sol = optimize(task=None, s2=s2, user_name=user_name, user_is_staff=user_is_staff,
# runMode=runMode, localsearch_time=localsearch_time, RUN_ENV=RUN_ENV, solver=SOLVER)
def create_graph(pot=None):
def hex_to_rgb(value):
value = value.lstrip('#')
lv = len(value)
return tuple(int(value[i:i + lv // 3], 16) for i in range(0, lv, lv // 3))
hex_colors = {
1: "#ffff99",
2: "#99ccff",
3: "#FFcc99",
4: "#CCFFCC",
5: "#CCCCFF",
6: "#9999FF",
}
rgb_colors = {}
for c in hex_colors:
rgb_colors[c] = hex_to_rgb(hex_colors[c])
G = nx.Graph()
node_colors = {}
node_label = {}
for t in teams:
node_label[t] = f"{t.shortname}"
if pot is None:
node_color = rgb_colors[t.pot]
node_colors[node_label[t]] = hex_colors[t.pot]
else:
node_color = rgb_colors[pot[t]]
node_colors[node_label[t]] = hex_colors[pot[t]]
G.add_node(node_label[t],
viz = {"color": {"a":0, "r": node_color[0], "g": node_color[1], "b": node_color[2]}, 'size':20})
# for n in nx.nodes(G):
# G.nodes[n]["viz"] = {}
# G.nodes[n]["viz"]["color"] = colors[]
for gq in gamereqs:
if gq.team1 in teams and gq.team2 in teams:
G.add_edge(node_label[gq.team1],node_label[gq.team2], capacity = 1.0)
SubG = [G.subgraph(c).copy() for c in nx.connected_components(G)]
# nx.draw(SubG[0], with_labels=True, font_weight='bold')
sub = SubG[0]
nx.draw(sub, with_labels=True,
node_size=400, font_size=6, node_color=[node_colors[g] for g in list(sub.nodes())])
pos = nx.nx_agraph.graphviz_layout(sub)
nx.draw_networkx_edge_labels(
sub, pos=pos, edge_labels={e: "" for e in list(sub.edges())}, font_color='black', font_size=6
)
nx.write_gexf(sub, "test.gexf")
distance = {}
max_path = 0
for t in teams:
path = nx.shortest_path(G, source=t.shortname)
for p in path:
if len(path[p]) <= 2:
length = 0
elif len(path[p]) == 3:
length = 1
else:
length = 2
distance[(teams.get(shortname=t.shortname),teams.get(shortname=p))] = length
# cut_value, partition = nx.minimum_cut(G, "Manch", "y")
return distance
# %%
distance = create_graph()
# %%
# import xpress as xp
# xp.controls.outputlog = 1
# model = xp.problem(name='Draws', sense=xp.minimize)
# model.setControl('maxtime' , 600)
# distance = {(t1,t2): 1 for t1 in teams for t2 in teams}
# for g in gamereqs:
# if (g.team1,g.team2) in distance.keys():
# distance[(g.team1,g.team2)] = 0
# groups = range(1,3)
# x = {}
# y = {}
# for g in groups:
# for t in teams:
# x[t,g] = xp.var(vartype=xp.binary)
# for t1,t2 in distance.keys():
# y[t1,t2] = xp.var(vartype=xp.binary)
# model.addVariable(x)
# model.addVariable(y)
# for t1,t2 in y.keys():
# for g in groups:
# model.addConstraint(y[t1,t2] >= x[t1,g] + x[t2,g] - 1)
# for t in teams:
# model.addConstraint(xp.Sum(x[t,g] for g in groups) == 1)
# for g in groups:
# model.addConstraint(xp.Sum(x[t,g] for t in teams) == len(teams)/len(groups))
# model.setObjective(xp.Sum(y[t1,t2]*distance[(t1,t2)] for (t1,t2) in y.keys()))
# start_time = time.time()
# model.solve()
# comp_time = time.time()-start_time
teams = Team.objects.filter(season=scenario.season,active=True).distinct()
import xpress as xp
xp.controls.outputlog = 1
model = xp.problem(name='Draws', sense=xp.minimize)
model.setControl('maxtime' , 600)
groups = range(1,5)
x = {}
y = {}
for g in groups:
for t in teams:
x[t,g] = xp.var(vartype=xp.binary)
for gr in gamereqs:
y[gr.team1,gr.team2,g] = xp.var(vartype=xp.binary)
model.addVariable(x)
model.addVariable(y)
for t1,t2,g in y.keys():
model.addConstraint(y[t1,t2,g] >= (x[t1,g] - x[t2,g]))
model.addConstraint(y[t1,t2,g] >= (x[t2,g] - x[t1,g]))
for t in teams:
model.addConstraint(xp.Sum(x[t,g] for g in groups) == 1)
for g in groups:
model.addConstraint(xp.Sum(x[t,g] for t in teams) == len(teams)/len(groups))
model.setObjective(xp.Sum(y[key] for key in y.keys()))
start_time = time.time()
model.solve()
comp_time = time.time()-start_time
# %%
pot = {}
group_list = {g:[] for g in groups}
for g in groups:
print("GROUP",g)
for t in teams:
if model.getSolution(x[t,g]) > 0:
print("\t",t.id)
group_list[g].append(t.id)
pot[t] = g
print("")
# %%
# %%
print(group_list)
# %%
create_graph(pot)

View File

@ -0,0 +1,705 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.tasks.optimize import optimize
from draws.solver.optimize_draws import ucl24_ha_matrix, ucl24_opponent_matrix
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from datetime import timedelta
from django.contrib.sessions.models import Session
def getVal(v):
if type(v) == int :
return v
else:
return v.value()
scenario = Scenario.objects.get(id=9402)
hawishes = HAWish.objects.filter(scenario=scenario,prio__in=['Hard','A'])
encwishes = EncWish.objects.filter(scenario=scenario,prio__in=['Hard','A'])
# %%
all_rounds = []
getDateByIso = {}
season = scenario.season
teams = Team.objects.filter(season=scenario.season,active=True)
higherHomeGames = defaultdict(lambda: [])
higherAwayGames = defaultdict(lambda: [])
higherDates = scenario.season.higherDates()
for game in scenario.season.higherGames():
higherHomeGames[game[1]].append(game)
higherAwayGames[game[2]].append(game)
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
all_rounds.append(higherRound)
getDateByIso[higherRound] = higherDates[game[0]]
higherTeams = set(list(higherHomeGames.keys()) + list(higherAwayGames.keys()))
gameRequirements = GameRequirement.objects.filter(scenario=scenario)
stadium_clashes = Pairing.objects.filter(scenario=scenario,type="Home",prio="Hard",active=True,team2__in=teams)
pairings = Pairing.objects.filter(scenario=scenario,active=True,team2__in=teams).exclude(id__in=stadium_clashes.values_list('id'))
encwishes = EncWish.objects.filter(scenario=scenario,prio__in=['Hard','A'])
hawishes = HAWish.objects.filter(scenario=scenario,prio__in=['Hard','A'])
pairings_dependencies = Pairing.objects.filter(scenario=scenario,active=True,team2__in=higherTeams)
days = Day.objects.filter(season=scenario.season, maxGames__gt=0)
blockings = Blocking.objects.filter(scenario=scenario)
uclpatterns = SpecialWish.objects.filter(scenario=scenario,name='UCL24Patterns',active=True).exists()
alternatestart = SpecialWish.objects.filter(scenario=scenario,name='AlternateStart',active=True).exists()
maxTourLength = season.maxTourLength
groups = Conference.objects.filter(scenario=scenario).filter(name__in=["UEL","UECL"])
uel_teams = list(groups.filter(name="UEL").first().teams.order_by('pot','country').values_list('id',flat=True))
uecl_teams = list(groups.filter(name="UECL").first().teams.order_by('pot','country').values_list('id',flat=True))
prioVal ={'A': 25 , 'B': 5 , 'C': 1, 'Hard' : 1000}
pairings_prio = {
p.id:prioVal[p.prio] for p in pairings
}
dependency_prio = {
p.id:prioVal[p.prio] for p in pairings_dependencies
}
daysPerRound = defaultdict(lambda:[])
# getRoundByDay = {}
# for d in days:
# daysPerRound[d.round].append(d)
# getRoundByDay[d.id] = d.round
getRoundByIso = {}
getIsoByRound = {}
getDateByDay = {}
for d in days:
getDateByDay[d] = datetime.datetime.strptime(d.day,"%Y-%m-%d")
iso = datetime.datetime.strptime(d.day,"%Y-%m-%d").isocalendar()
getRoundByIso[f"{iso.year}-{iso.week}"] = d.round
getIsoByRound[d.round] = f"{iso.year}-{iso.week}"
all_rounds.append(f"{iso.year}-{iso.week}")
getDateByIso[f"{iso.year}-{iso.week}"] = getDateByDay[d]
daysPerRound[f"{iso.year}-{iso.week}"].append(d)
all_rounds = sorted(list(set(all_rounds)))
single_day_rounds = [r for r in daysPerRound if len(daysPerRound[r]) == 1]
two_day_rounds = [r for r in daysPerRound if len(daysPerRound[r]) == 2 ]
multi_day_rounds = [r for r in daysPerRound if len(daysPerRound[r]) >= 3 ]
team_ids = list(teams.values_list('id',flat=True))
getTeamByID = {
t.id:t for t in teams
}
# list all rounds where each day is blocked for a team
blockedRounds = {(t.id,r):True for r in all_rounds for t in teams}
for t in teams:
tblocks = blockings.filter(team=t)
for r in all_rounds:
for d in daysPerRound[r]:
if not tblocks.filter(day=d).exists():
blockedRounds[(t.id,r)] = False
break
gamereqs = []
opponents_from_pot = defaultdict(lambda:defaultdict(lambda:[]))
for req in gameRequirements:
gamereqs.append((req.team1.id,req.team2.id))
opponents_from_pot[req.team1.id][req.team2.pot].append(req.team2.id)
opponents_from_pot[req.team2.id][req.team1.pot].append(req.team1.id)
pot = {}
teams_in_pot = {}
for i in teams.values_list('pot',flat=True).distinct():
pot[i] = teams.filter(pot=i)
teams_in_pot[i] = list(teams.filter(pot=i).values_list('id',flat=True))
topTeams = teams.filter(attractivity__gte=4)
topGames = [(t1.id,t2.id) for t1 in topTeams for t2 in topTeams if (t1.id,t2.id) in gamereqs]
topTeam_clashes = {t.id:[] for t in topTeams}
for t in topTeams:
for pair in stadium_clashes.filter(team1=t):
topTeam_clashes[t.id].append(pair.team2.id)
for pair in stadium_clashes.filter(team2=t):
topTeam_clashes[t.id].append(pair.team1.id)
rounds = all_rounds
ucl_rounds = [r for i,r in enumerate(rounds) if i in [0,2,3,4,5,6,8,9]]
uel_rounds = [r for i,r in enumerate(rounds) if i in [1,2,3,4,5,6,8,9]]
uecl_rounds = [r for i,r in enumerate(rounds) if i in [2,3,4,5,6,7]]
model = pulp.LpProblem(f"test", pulp.LpMinimize)
dummy = pulp.LpVariable("Dummy", lowBound=1, cat=pulp.LpContinuous)
x = { (r,t1,t2) : pulp.LpVariable('x_'+str(r)+'_'+str(t1)+'_'+str(t2) , lowBound = 0, upBound = 1, cat = pulp.LpContinuous) for r in rounds for t1 in team_ids for t2 in team_ids if (t1,t2) in gamereqs or (t2,t1) in gamereqs}
home = {(r,t) : pulp.LpVariable('home_'+str(r)+'_'+str(t) , lowBound = 0, upBound = 1, cat = pulp.LpContinuous) for r in rounds for t in team_ids}
away = {(r,t) : pulp.LpVariable('away_'+str(r)+'_'+str(t) , lowBound = 0, upBound = 1, cat = pulp.LpContinuous) for r in rounds for t in team_ids}
y = {(r,t) : pulp.LpVariable('y_'+str(r)+'_'+str(t) , lowBound = 0, upBound = 1, cat = pulp.LpInteger) for r in rounds for t in team_ids}
team_viol = {t : pulp.LpVariable('team_viol_'+str(t) , lowBound = 0, cat = pulp.LpContinuous) for t in team_ids}
dependencyViolation = {(r,t,t2) : pulp.LpVariable('dependencyViol_'+str(r)+"_"+str(t)+"_"+str(t2) , lowBound = 0, cat = pulp.LpContinuous) for r in rounds for t in team_ids for t2 in team_ids+list(higherHomeGames.keys())}
blockingViolation = { (r,t) : pulp.LpVariable('blockingViolation_'+ str(r) +'_'+str(t) , lowBound = 0, cat = pulp.LpContinuous) for t in team_ids for r in rounds}
# %%
# model += home['2024-51',42286] == 1
# model += x[('2024-50', 42279, 42278)] == 0
# for key in x.keys():
# # if key[0] >= '2024-45':
# x[key].cat = pulp.LpInteger
# each game has to be played
for (t1,t2) in gamereqs:
model += lpSum([x[r,t1,t2] for r in rounds]) == 1
for r in uel_rounds:
model += lpSum(home[r,t] for t in uel_teams) == lpSum(away[r,t] for t in uel_teams)
for r in uecl_rounds:
model += lpSum(home[r,t] for t in uecl_teams) == lpSum(away[r,t] for t in uecl_teams)
for t in team_ids:
for r in rounds:
model += y[r,t] >= home[r,t] - 0.8
model += y[r,t] >= away[r,t] - 0.8
if t in uecl_teams:
model += lpSum(home[r,t] for r in rounds) == lpSum(away[r,t] for r in rounds)
for r in [i for i in rounds if i not in uecl_rounds]:
model += home[r,t] + away[r,t] <= 0
for r in uecl_rounds:
# each team plays once in each round
model += lpSum([x[r,t,t2]+x[r,t2,t] for t2 in team_ids if (r,t,t2) in x.keys()]) == 1
model += home[r,t] + away[r,t] == 1
# blockings are hard restrictions
if blockedRounds[(t,r)]:
model += home[r,t] == blockingViolation[r,t]
for r in rounds:
# couple homes
# model += home[r,t] == lpSum([x[r,t,t2] for t2 in team_ids if (r,t,t2) in x.keys()])
# model += away[r,t] == lpSum([x[r,t2,t] for t2 in team_ids if (r,t2,t) in x.keys()])
for t2 in team_ids:
if (r,t,t2) in x.keys():
model += home[r,t] >= x[r,t,t2]
model += away[r,t] >= x[r,t2,t]
# always play alternating end of season
model += lpSum([home[r2,t] for r2 in list(uecl_rounds)[-2:]]) <= 1
model += lpSum([away[r2,t] for r2 in list(uecl_rounds)[-2:]]) <= 1
# alternating start of season
model += lpSum([home[r2,t] for r2 in uecl_rounds[:2]]) <= 1
model += lpSum([away[r2,t] for r2 in uecl_rounds[:2]]) <= 1
# no more than 2 consecutive homegames/awaygames
for r in range(1,len(uecl_rounds)-1):
model += lpSum([away[r2,t] for r2 in uecl_rounds[r:r+3]]) <= 2
model += lpSum([home[r2,t] for r2 in uecl_rounds[r:r+3]]) <= 2
elif t in uel_teams:
model += lpSum(home[r,t] for r in rounds) == lpSum(away[r,t] for r in rounds)
for r in [i for i in rounds if i not in uel_rounds]:
model += home[r,t] + away[r,t] <= 0
for r in uel_rounds:
# each team plays once in each round
model += lpSum([x[r,t,t2]+x[r,t2,t] for t2 in team_ids if (r,t,t2) in x.keys()]) == 1
model += home[r,t] + away[r,t] == 1
# blockings are hard restrictions
if blockedRounds[(t,r)]:
model += home[r,t] == blockingViolation[r,t]
for r in rounds:
# couple homes
# model += home[r,t] == lpSum([x[r,t,t2] for t2 in team_ids if (r,t,t2) in x.keys()])
# model += away[r,t] == lpSum([x[r,t2,t] for t2 in team_ids if (r,t2,t) in x.keys()])
for t2 in team_ids:
if (r,t,t2) in x.keys():
model += home[r,t] >= x[r,t,t2]
model += away[r,t] >= x[r,t2,t]
# always play alternating end of season
model += lpSum([home[r2,t] for r2 in list(uel_rounds)[-2:]]) <= 1
model += lpSum([away[r2,t] for r2 in list(uel_rounds)[-2:]]) <= 1
# alternating start of season
model += lpSum([home[r2,t] for r2 in uel_rounds[:2]]) <= 1
model += lpSum([away[r2,t] for r2 in uel_rounds[:2]]) <= 1
# no more than 2 consecutive homegames/awaygames
for r in range(1,len(uel_rounds)-1):
model += lpSum([home[r2,t] for r2 in uel_rounds[r:r+3]]) <= 2
model += lpSum([away[r2,t] for r2 in uel_rounds[r:r+3]]) <= 2
team_pairing = defaultdict(lambda:[])
# PAIRINGDIST = ((0, _('do not play both on same day')), (1, _('do not play both within two successive days')), (8, _('do not play both within three successive days')),
# (2, _('do not play both at the same time')), (3, _('do not play both in the same round')),(10, _('do not play both on same weekend (Fr.-Mo.)')),
# (4, _('play both on same day')), (5, _('play both within two successive days')), (9, _('play both within three successive days')),
# (6, _('play both at the same time')), (7, _('play both in the same round')), (11, _('play both on same weekend (Fr.-Mo.)')),
# stadium/city clashes + pairings
for r in single_day_rounds:
for pair in stadium_clashes.filter(dist__in=[0,1,3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED STADIUM single {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
for pair in pairings.filter(dist__in=[0,1,3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
# print(f"ADDED PAIRING single {pair}")
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED PAIRING single {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
if pair.type == 'Home and Away':
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) >= 1 - dependencyViolation[r,pair.team1.id,pair.team2.id]
for r in two_day_rounds:
for pair in stadium_clashes.filter(dist__in=[1,3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED STADIUM twoday {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
for pair in pairings.filter(dist__in=[1,3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED PAIRING multi {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
if pair.type == 'Home and Away':
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) >= 1 - dependencyViolation[r,pair.team1.id,pair.team2.id]
for r in multi_day_rounds:
for pair in stadium_clashes.filter(dist__in=[3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED STADIUM multi {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
for pair in pairings.filter(dist__in=[3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED PAIRING multi {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
if pair.type == 'Home and Away':
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) >= 1 - dependencyViolation[r,pair.team1.id,pair.team2.id]
ucl_home = defaultdict(lambda:[])
ucl_away = defaultdict(lambda:[])
# Season Dependencies
for p in pairings_dependencies.filter(dist__in=[3,8]): # do not play same round
team_pairing[p.team1.id].append(p.team2.shortname)
team_pairing[p.team2.id].append(p.team1.shortname)
for game in higherHomeGames[p.team2.id]:
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
ucl_home[p.team2].append(higherRound)
if higherRound in single_day_rounds:
if p.team1.id in uel_teams and higherRound in uel_rounds:
model += away[higherRound,p.team1.id] >= 1 - dependencyViolation[higherRound,p.team1.id,p.team2.id]
elif p.team1.id in uecl_teams and higherRound in uecl_rounds:
model += away[higherRound,p.team1.id] >= 1 - dependencyViolation[higherRound,p.team1.id,p.team2.id]
for game in higherAwayGames[p.team2.id]:
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
ucl_away[p.team2].append(higherRound)
for p in pairings_dependencies.filter(dist__in=[0,1]): # do not play same day/two days
team_pairing[p.team1.id].append(p.team2.shortname)
team_pairing[p.team2.id].append(p.team1.shortname)
for game in higherHomeGames[p.team2.id]:
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
ucl_home[p.team2].append(higherRound)
if p.dist == 0:
forbidden_days = [higherDates[game[0]].date()]
elif p.dist == 1:
forbidden_days = [higherDates[game[0]].date() - timedelta(days=1),higherDates[game[0]].date(),higherDates[game[0]].date() + timedelta(days=1)]
available_days = [d for d in daysPerRound[higherRound] if getDateByDay[d].date() not in forbidden_days]
if not available_days:
if p.team1.id in uel_teams and higherRound in uel_rounds:
model += away[higherRound,p.team1.id] >= 1 - dependencyViolation[higherRound,p.team1.id,p.team2.id]
elif p.team1.id in uecl_teams and higherRound in uecl_rounds:
model += away[higherRound,p.team1.id] >= 1 - dependencyViolation[higherRound,p.team1.id,p.team2.id]
for game in higherAwayGames[p.team2.id]:
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
ucl_away[p.team2].append(higherRound)
# model += home['2024-40',42339] == 1
# model += home['2024-43',42339] == 0
# model += home['2024-45',42339] == 1
# model += home['2024-48',42339] == 0
# model += home['2024-50',42339] == 1
# model += home['2024-51',42339] == 0
# model += home['2024-40',42278] == 0
# model += x[('2024-43',42278,42339)] == 1
# model += x[('2024-40',42339,42340)] == 1
# model += home['2024-51',42339] == 0
# model += home["2024-51",42286] <= 0
# minimize pairing violation
objective_function = dummy +\
lpSum(10*y[key] for key in y.keys()) +\
lpSum(home[key] for key in home.keys()) +\
lpSum(away[key] for key in away.keys()) +\
10000*lpSum(dependencyViolation[key] for key in dependencyViolation.keys()) +\
10000*lpSum(blockingViolation[key] for key in blockingViolation.keys())
model += objective_function #+ 0.001*random_seed
with open ("basicmodel.txt", "w") as f:
f.write(model.__repr__())
model.solve(XPRESS(msg=1,maxSeconds=300, gapRel=0))
# FOR DEBUGGING
nDays = len(rounds)
home_dict = {}
away_dict = {}
viol_dict = {}
for key in home.keys():
if getVal(home[key]) and getVal(home[key]) > 0.95:
home_dict[key[0],key[1]] = "H"
for key in away.keys():
if getVal(away[key]) and getVal(away[key]) > 0.95:
away_dict[key[0],key[1]] = "A"
for key in dependencyViolation.keys():
if getVal(dependencyViolation[key]) and getVal(dependencyViolation[key]) > 0:
print("VIOLATED DEPENDENCY",key,getVal(dependencyViolation[key]))
viol_dict[key[0],key[1]] = Team.objects.get(id=key[2])
for key in blockingViolation.keys():
if getVal(blockingViolation[key]) and getVal(blockingViolation[key]) > 0:
print("VIOLATED BLOCKING",key,getVal(blockingViolation[key]))
viol_dict[key[0],key[1]] = key[0]
for key in x.keys():
if getVal(x[key]) and getVal(x[key]) > 0.95:
print(key,getVal(x[key]))
print(r[0],teams.get(id=key[1]),teams.get(id=key[2]))
home_dict[key[0],key[1]] = f"{teams.get(id=key[2])}"
away_dict[key[0],key[2]] = f"@{teams.get(id=key[1])}"
for k,v in team_pairing.items():
team_pairing[k] = ",".join(set(v))
sol = " \
<style> \
table, th, td { \
border: 1px solid black; \
border-collapse: collapse; \
} \
</style> \
"
sol += "<table style='border:1px solid black'>\n"
sol += "<thead>\n"
sol += "<tr><th></th><th></th><th></th><th></th><th></th><th></th><th></th>"
for d in all_rounds:
sol += f"<th>{d} - {getDateByIso[d].date()}</th>"
sol += "</tr>"
sol += "</thead>\n"
sol += "<tbody>\n"
for t in ucl_home:
sol += f"<tr><td>UCL</t><td>{t.id}</td><td>Pot {t.pot}</td><td>{t.country}</td><td>{t.name}</td><td>{t.shortname}</td><td>{team_pairing[t.id]}</td>"
for d in all_rounds:
if d in ucl_rounds:
if d in ucl_home[t]:
fontcolor = 'black'
bgcolor = 'lightsteelblue'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>H</td>"
elif d in ucl_away[t]:
fontcolor = 'black'
bgcolor = 'lightyellow'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>A</td>"
else:
sol += "<td></td>"
else:
sol += "<td style='background-color:lightgrey'></td>"
sol += "</tr>"
sol += "<tr style='background-color:lightgrey' ><th colspan='7'>UEL</th><th></th><th>1</th><th>2</th><th>3</th><th>4</th><th>5</th><th>6</th><th></th><th>7</th><th>8</th></tr>"
for t in uel_teams:
tname = getTeamByID[t].name
tshortname = getTeamByID[t].shortname
tcountry = getTeamByID[t].country
tpot = getTeamByID[t].pot
sol += f"<tr><td>UEL</t><td>{t}</td><td>Pot {tpot}</td><td>{tcountry}</td><td>{tname}</td><td>{tshortname}</td><td>{team_pairing[t]}</td>"
for d in all_rounds:
if d in uel_rounds:
if (d,t) in home_dict.keys():
fontcolor = 'black'
bgcolor = 'lightsteelblue'
if (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{home_dict[(d,t)]}</td>"
elif (d,t) in away_dict.keys():
fontcolor = 'black'
bgcolor = 'lightyellow'
if (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{away_dict[(d,t)]}</td>"
elif (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{viol_dict[(d,t)]}</td>"
else:
sol += "<td></td>"
else:
sol += "<td style='background-color:lightgrey'></td>"
sol += "</tr>"
sol += "<tr style='background-color:lightgrey'><th colspan='7'>UECL</th><th></th><th></th><th>1</th><th>2</th><th>3</th><th>4</th><th>5</th><th>6</th><th></th><th></th></tr>"
for t in uecl_teams:
tname = getTeamByID[t].name
tshortname = getTeamByID[t].shortname
tcountry = getTeamByID[t].country
tpot = getTeamByID[t].pot
sol += f"<tr><td>UECL</t><td>{t}</td><td>Pot {tpot}</td><td>{tcountry}</td><td>{tname}</td><td>{tshortname}</td><td>{team_pairing[t]}</td>"
for d in all_rounds:
if d in uecl_rounds:
# if (d,t) in viol_dict.keys():
# fontcolor = 'white'
# bgcolor = 'darkred'
# sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{viol_dict[(d,t)]}</td>"
if (d,t) in home_dict.keys():
fontcolor = 'black'
bgcolor = 'lightsteelblue'
if (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{home_dict[(d,t)]}</td>"
elif (d,t) in away_dict.keys():
fontcolor = 'black'
bgcolor = 'lightyellow'
if (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{away_dict[(d,t)]}</td>"
elif (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{viol_dict[(d,t)]}</td>"
else:
sol += "<td></td>"
else:
sol += "<td style='background-color:lightgrey'></td>"
sol += "</tr>"
sol += "</tbody>\n"
sol += "</table>\n"
with open(f'ueluecl24_debug.html', 'w') as f:
f.write(sol)
# %%

View File

@ -0,0 +1,705 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.tasks.optimize import optimize
from draws.solver.optimize_draws import ucl24_ha_matrix, ucl24_opponent_matrix
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from datetime import timedelta
from django.contrib.sessions.models import Session
def getVal(v):
if type(v) == int :
return v
else:
return v.value()
scenario = Scenario.objects.get(id=9306)
hawishes = HAWish.objects.filter(scenario=scenario,prio__in=['Hard','A'])
encwishes = EncWish.objects.filter(scenario=scenario,prio__in=['Hard','A'])
# %%
all_rounds = []
getDateByIso = {}
season = scenario.season
teams = Team.objects.filter(season=scenario.season,active=True)
higherHomeGames = defaultdict(lambda: [])
higherAwayGames = defaultdict(lambda: [])
higherDates = scenario.season.higherDates()
for game in scenario.season.higherGames():
higherHomeGames[game[1]].append(game)
higherAwayGames[game[2]].append(game)
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
all_rounds.append(higherRound)
getDateByIso[higherRound] = higherDates[game[0]]
higherTeams = set(list(higherHomeGames.keys()) + list(higherAwayGames.keys()))
gameRequirements = GameRequirement.objects.filter(scenario=scenario)
stadium_clashes = Pairing.objects.filter(scenario=scenario,type="Home",prio="Hard",active=True,team2__in=teams)
pairings = Pairing.objects.filter(scenario=scenario,active=True,team2__in=teams).exclude(id__in=stadium_clashes.values_list('id'))
encwishes = EncWish.objects.filter(scenario=scenario,prio__in=['Hard','A'])
hawishes = HAWish.objects.filter(scenario=scenario,prio__in=['Hard','A'])
pairings_dependencies = Pairing.objects.filter(scenario=scenario,active=True,team2__in=higherTeams)
days = Day.objects.filter(season=scenario.season, maxGames__gt=0)
blockings = Blocking.objects.filter(scenario=scenario)
uclpatterns = SpecialWish.objects.filter(scenario=scenario,name='UCL24Patterns',active=True).exists()
alternatestart = SpecialWish.objects.filter(scenario=scenario,name='AlternateStart',active=True).exists()
maxTourLength = season.maxTourLength
groups = Conference.objects.filter(scenario=scenario).filter(name__in=["UEL","UECL"])
uel_teams = list(groups.filter(name="UEL").first().teams.order_by('pot','country').values_list('id',flat=True))
uecl_teams = list(groups.filter(name="UECL").first().teams.order_by('pot','country').values_list('id',flat=True))
prioVal ={'A': 25 , 'B': 5 , 'C': 1, 'Hard' : 1000}
pairings_prio = {
p.id:prioVal[p.prio] for p in pairings
}
dependency_prio = {
p.id:prioVal[p.prio] for p in pairings_dependencies
}
daysPerRound = defaultdict(lambda:[])
# getRoundByDay = {}
# for d in days:
# daysPerRound[d.round].append(d)
# getRoundByDay[d.id] = d.round
getRoundByIso = {}
getIsoByRound = {}
getDateByDay = {}
for d in days:
getDateByDay[d] = datetime.datetime.strptime(d.day,"%Y-%m-%d")
iso = datetime.datetime.strptime(d.day,"%Y-%m-%d").isocalendar()
getRoundByIso[f"{iso.year}-{iso.week}"] = d.round
getIsoByRound[d.round] = f"{iso.year}-{iso.week}"
all_rounds.append(f"{iso.year}-{iso.week}")
getDateByIso[f"{iso.year}-{iso.week}"] = getDateByDay[d]
daysPerRound[f"{iso.year}-{iso.week}"].append(d)
all_rounds = sorted(list(set(all_rounds)))
single_day_rounds = [r for r in daysPerRound if len(daysPerRound[r]) == 1]
two_day_rounds = [r for r in daysPerRound if len(daysPerRound[r]) == 2 ]
multi_day_rounds = [r for r in daysPerRound if len(daysPerRound[r]) >= 3 ]
team_ids = list(teams.values_list('id',flat=True))
getTeamByID = {
t.id:t for t in teams
}
# list all rounds where each day is blocked for a team
blockedRounds = {(t.id,r):True for r in all_rounds for t in teams}
for t in teams:
tblocks = blockings.filter(team=t)
for r in all_rounds:
for d in daysPerRound[r]:
if not tblocks.filter(day=d).exists():
blockedRounds[(t.id,r)] = False
break
gamereqs = []
opponents_from_pot = defaultdict(lambda:defaultdict(lambda:[]))
for req in gameRequirements:
gamereqs.append((req.team1.id,req.team2.id))
opponents_from_pot[req.team1.id][req.team2.pot].append(req.team2.id)
opponents_from_pot[req.team2.id][req.team1.pot].append(req.team1.id)
pot = {}
teams_in_pot = {}
for i in teams.values_list('pot',flat=True).distinct():
pot[i] = teams.filter(pot=i)
teams_in_pot[i] = list(teams.filter(pot=i).values_list('id',flat=True))
topTeams = teams.filter(attractivity__gte=4)
topGames = [(t1.id,t2.id) for t1 in topTeams for t2 in topTeams if (t1.id,t2.id) in gamereqs]
topTeam_clashes = {t.id:[] for t in topTeams}
for t in topTeams:
for pair in stadium_clashes.filter(team1=t):
topTeam_clashes[t.id].append(pair.team2.id)
for pair in stadium_clashes.filter(team2=t):
topTeam_clashes[t.id].append(pair.team1.id)
rounds = all_rounds
ucl_rounds = [r for i,r in enumerate(rounds) if i in [0,2,3,4,5,6,8,9]]
uel_rounds = [r for i,r in enumerate(rounds) if i in [1,2,3,4,5,6,8,9]]
uecl_rounds = [r for i,r in enumerate(rounds) if i in [2,3,4,5,6,7]]
model = pulp.LpProblem(f"test", pulp.LpMinimize)
dummy = pulp.LpVariable("Dummy", lowBound=1, cat=pulp.LpContinuous)
x = { (r,t1,t2) : pulp.LpVariable('x_'+str(r)+'_'+str(t1)+'_'+str(t2) , lowBound = 0, upBound = 1, cat = pulp.LpContinuous) for r in rounds for t1 in team_ids for t2 in team_ids if (t1,t2) in gamereqs or (t2,t1) in gamereqs}
home = {(r,t) : pulp.LpVariable('home_'+str(r)+'_'+str(t) , lowBound = 0, upBound = 1, cat = pulp.LpContinuous) for r in rounds for t in team_ids}
away = {(r,t) : pulp.LpVariable('away_'+str(r)+'_'+str(t) , lowBound = 0, upBound = 1, cat = pulp.LpContinuous) for r in rounds for t in team_ids}
y = {(r,t) : pulp.LpVariable('y_'+str(r)+'_'+str(t) , lowBound = 0, upBound = 1, cat = pulp.LpInteger) for r in rounds for t in team_ids}
team_viol = {t : pulp.LpVariable('team_viol_'+str(t) , lowBound = 0, cat = pulp.LpContinuous) for t in team_ids}
dependencyViolation = {(r,t,t2) : pulp.LpVariable('dependencyViol_'+str(r)+"_"+str(t)+"_"+str(t2) , lowBound = 0, cat = pulp.LpContinuous) for r in rounds for t in team_ids for t2 in team_ids+list(higherHomeGames.keys())}
blockingViolation = { (r,t) : pulp.LpVariable('blockingViolation_'+ str(r) +'_'+str(t) , lowBound = 0, cat = pulp.LpContinuous) for t in team_ids for r in rounds}
# %%
# model += home['2024-51',42286] == 1
# model += x[('2024-50', 42279, 42278)] == 0
# for key in x.keys():
# # if key[0] >= '2024-45':
# x[key].cat = pulp.LpInteger
# each game has to be played
for (t1,t2) in gamereqs:
model += lpSum([x[r,t1,t2] for r in rounds]) == 1
for r in uel_rounds:
model += lpSum(home[r,t] for t in uel_teams) == lpSum(away[r,t] for t in uel_teams)
for r in uecl_rounds:
model += lpSum(home[r,t] for t in uecl_teams) == lpSum(away[r,t] for t in uecl_teams)
for t in team_ids:
for r in rounds:
model += y[r,t] >= home[r,t] - 0.8
model += y[r,t] >= away[r,t] - 0.8
if t in uecl_teams:
model += lpSum(home[r,t] for r in rounds) == lpSum(away[r,t] for r in rounds)
for r in [i for i in rounds if i not in uecl_rounds]:
model += home[r,t] + away[r,t] <= 0
for r in uecl_rounds:
# each team plays once in each round
model += lpSum([x[r,t,t2]+x[r,t2,t] for t2 in team_ids if (r,t,t2) in x.keys()]) == 1
model += home[r,t] + away[r,t] == 1
# blockings are hard restrictions
if blockedRounds[(t,r)]:
model += home[r,t] == blockingViolation[r,t]
for r in rounds:
# couple homes
# model += home[r,t] == lpSum([x[r,t,t2] for t2 in team_ids if (r,t,t2) in x.keys()])
# model += away[r,t] == lpSum([x[r,t2,t] for t2 in team_ids if (r,t2,t) in x.keys()])
for t2 in team_ids:
if (r,t,t2) in x.keys():
model += home[r,t] >= x[r,t,t2]
model += away[r,t] >= x[r,t2,t]
# always play alternating end of season
model += lpSum([home[r2,t] for r2 in list(uecl_rounds)[-2:]]) <= 1
model += lpSum([away[r2,t] for r2 in list(uecl_rounds)[-2:]]) <= 1
# alternating start of season
model += lpSum([home[r2,t] for r2 in uecl_rounds[:2]]) <= 1
model += lpSum([away[r2,t] for r2 in uecl_rounds[:2]]) <= 1
# no more than 2 consecutive homegames/awaygames
for r in range(1,len(uecl_rounds)-1):
model += lpSum([away[r2,t] for r2 in uecl_rounds[r:r+3]]) <= 2
model += lpSum([home[r2,t] for r2 in uecl_rounds[r:r+3]]) <= 2
elif t in uel_teams:
model += lpSum(home[r,t] for r in rounds) == lpSum(away[r,t] for r in rounds)
for r in [i for i in rounds if i not in uel_rounds]:
model += home[r,t] + away[r,t] <= 0
for r in uel_rounds:
# each team plays once in each round
model += lpSum([x[r,t,t2]+x[r,t2,t] for t2 in team_ids if (r,t,t2) in x.keys()]) == 1
model += home[r,t] + away[r,t] == 1
# blockings are hard restrictions
if blockedRounds[(t,r)]:
model += home[r,t] == blockingViolation[r,t]
for r in rounds:
# couple homes
# model += home[r,t] == lpSum([x[r,t,t2] for t2 in team_ids if (r,t,t2) in x.keys()])
# model += away[r,t] == lpSum([x[r,t2,t] for t2 in team_ids if (r,t2,t) in x.keys()])
for t2 in team_ids:
if (r,t,t2) in x.keys():
model += home[r,t] >= x[r,t,t2]
model += away[r,t] >= x[r,t2,t]
# always play alternating end of season
model += lpSum([home[r2,t] for r2 in list(uel_rounds)[-2:]]) <= 1
model += lpSum([away[r2,t] for r2 in list(uel_rounds)[-2:]]) <= 1
# alternating start of season
model += lpSum([home[r2,t] for r2 in uel_rounds[:2]]) <= 1
model += lpSum([away[r2,t] for r2 in uel_rounds[:2]]) <= 1
# no more than 2 consecutive homegames/awaygames
for r in range(1,len(uel_rounds)-1):
model += lpSum([home[r2,t] for r2 in uel_rounds[r:r+3]]) <= 2
model += lpSum([away[r2,t] for r2 in uel_rounds[r:r+3]]) <= 2
team_pairing = defaultdict(lambda:[])
# PAIRINGDIST = ((0, _('do not play both on same day')), (1, _('do not play both within two successive days')), (8, _('do not play both within three successive days')),
# (2, _('do not play both at the same time')), (3, _('do not play both in the same round')),(10, _('do not play both on same weekend (Fr.-Mo.)')),
# (4, _('play both on same day')), (5, _('play both within two successive days')), (9, _('play both within three successive days')),
# (6, _('play both at the same time')), (7, _('play both in the same round')), (11, _('play both on same weekend (Fr.-Mo.)')),
# stadium/city clashes + pairings
for r in single_day_rounds:
for pair in stadium_clashes.filter(dist__in=[0,1,3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED STADIUM single {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
for pair in pairings.filter(dist__in=[0,1,3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
# print(f"ADDED PAIRING single {pair}")
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED PAIRING single {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
if pair.type == 'Home and Away':
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) >= 1 - dependencyViolation[r,pair.team1.id,pair.team2.id]
for r in two_day_rounds:
for pair in stadium_clashes.filter(dist__in=[1,3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED STADIUM twoday {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
for pair in pairings.filter(dist__in=[1,3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED PAIRING multi {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
if pair.type == 'Home and Away':
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) >= 1 - dependencyViolation[r,pair.team1.id,pair.team2.id]
for r in multi_day_rounds:
for pair in stadium_clashes.filter(dist__in=[3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED STADIUM multi {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
for pair in pairings.filter(dist__in=[3,8]):
team_pairing[pair.team1.id].append(pair.team2.shortname)
team_pairing[pair.team2.id].append(pair.team1.shortname)
fullseason = True
iso1 = all_rounds[0]
iso2 = all_rounds[-1]
if pair.first_day:
iso1 = pair.first_day.getDate().isocalendar()
iso1 = f"{iso.year}-{iso.week}"
fullseason = False
if pair.last_day:
iso2 = pair.last_day.getDate().isocalendar()
iso2 = f"{iso.year}-{iso.week}"
fullseason = False
if fullseason or (iso1 <= r and r <= iso2):
if pair.team1.id in uel_teams and (r not in uel_rounds):
continue
if pair.team1.id in uecl_teams and (r not in uecl_rounds):
continue
if pair.team2.id in uel_teams and (r not in uel_rounds):
continue
if pair.team2.id in uecl_teams and (r not in uecl_rounds):
continue
print(r, f"ADDED PAIRING multi {pair}")
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) <= 1 + dependencyViolation[r,pair.team1.id,pair.team2.id]
model += home[r,pair.team1.id] <= away[r,pair.team2.id] + dependencyViolation[r,pair.team1.id,pair.team2.id]
if pair.type == 'Home and Away':
model += lpSum(home[r,pair.team1.id]+home[r,pair.team2.id]) >= 1 - dependencyViolation[r,pair.team1.id,pair.team2.id]
ucl_home = defaultdict(lambda:[])
ucl_away = defaultdict(lambda:[])
# Season Dependencies
for p in pairings_dependencies.filter(dist__in=[3,8]): # do not play same round
team_pairing[p.team1.id].append(p.team2.shortname)
team_pairing[p.team2.id].append(p.team1.shortname)
for game in higherHomeGames[p.team2.id]:
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
ucl_home[p.team2].append(higherRound)
if higherRound in single_day_rounds:
if p.team1.id in uel_teams and higherRound in uel_rounds:
model += away[higherRound,p.team1.id] >= 1 - dependencyViolation[higherRound,p.team1.id,p.team2.id]
elif p.team1.id in uecl_teams and higherRound in uecl_rounds:
model += away[higherRound,p.team1.id] >= 1 - dependencyViolation[higherRound,p.team1.id,p.team2.id]
for game in higherAwayGames[p.team2.id]:
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
ucl_away[p.team2].append(higherRound)
for p in pairings_dependencies.filter(dist__in=[0,1]): # do not play same day/two days
team_pairing[p.team1.id].append(p.team2.shortname)
team_pairing[p.team2.id].append(p.team1.shortname)
for game in higherHomeGames[p.team2.id]:
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
ucl_home[p.team2].append(higherRound)
if p.dist == 0:
forbidden_days = [higherDates[game[0]].date()]
elif p.dist == 1:
forbidden_days = [higherDates[game[0]].date() - timedelta(days=1),higherDates[game[0]].date(),higherDates[game[0]].date() + timedelta(days=1)]
available_days = [d for d in daysPerRound[higherRound] if getDateByDay[d].date() not in forbidden_days]
if not available_days:
if p.team1.id in uel_teams and higherRound in uel_rounds:
model += away[higherRound,p.team1.id] >= 1 - dependencyViolation[higherRound,p.team1.id,p.team2.id]
elif p.team1.id in uecl_teams and higherRound in uecl_rounds:
model += away[higherRound,p.team1.id] >= 1 - dependencyViolation[higherRound,p.team1.id,p.team2.id]
for game in higherAwayGames[p.team2.id]:
higherRound = f"{higherDates[game[0]].isocalendar().year}-{higherDates[game[0]].isocalendar().week}"
ucl_away[p.team2].append(higherRound)
model += home['2024-40',42339] == 1
model += home['2024-43',42339] == 0
model += home['2024-45',42339] == 1
model += home['2024-48',42339] == 0
model += home['2024-50',42339] == 1
model += home['2024-51',42339] == 0
model += home['2024-40',42278] == 0
model += x[('2024-43',42278,42339)] == 1
model += x[('2024-40',42339,42340)] == 1
model += home['2024-51',42339] == 0
model += home["2024-51",42286] <= 0
# minimize pairing violation
objective_function = dummy +\
lpSum(10*y[key] for key in y.keys()) +\
lpSum(home[key] for key in home.keys()) +\
lpSum(away[key] for key in away.keys()) +\
10000*lpSum(dependencyViolation[key] for key in dependencyViolation.keys()) +\
10000*lpSum(blockingViolation[key] for key in blockingViolation.keys())
model += objective_function #+ 0.001*random_seed
with open ("basicmodel.txt", "w") as f:
f.write(model.__repr__())
model.solve(XPRESS(msg=1,maxSeconds=300, gapRel=0))
# FOR DEBUGGING
nDays = len(rounds)
home_dict = {}
away_dict = {}
viol_dict = {}
for key in home.keys():
if getVal(home[key]) and getVal(home[key]) > 0.95:
home_dict[key[0],key[1]] = "H"
for key in away.keys():
if getVal(away[key]) and getVal(away[key]) > 0.95:
away_dict[key[0],key[1]] = "A"
for key in dependencyViolation.keys():
if getVal(dependencyViolation[key]) and getVal(dependencyViolation[key]) > 0:
print("VIOLATED DEPENDENCY",key,getVal(dependencyViolation[key]))
viol_dict[key[0],key[1]] = Team.objects.get(id=key[2])
for key in blockingViolation.keys():
if getVal(blockingViolation[key]) and getVal(blockingViolation[key]) > 0:
print("VIOLATED BLOCKING",key,getVal(blockingViolation[key]))
viol_dict[key[0],key[1]] = key[0]
for key in x.keys():
if getVal(x[key]) and getVal(x[key]) > 0.95:
print(key,getVal(x[key]))
print(r[0],teams.get(id=key[1]),teams.get(id=key[2]))
home_dict[key[0],key[1]] = f"{teams.get(id=key[2])}"
away_dict[key[0],key[2]] = f"@{teams.get(id=key[1])}"
for k,v in team_pairing.items():
team_pairing[k] = ",".join(set(v))
sol = " \
<style> \
table, th, td { \
border: 1px solid black; \
border-collapse: collapse; \
} \
</style> \
"
sol += "<table style='border:1px solid black'>\n"
sol += "<thead>\n"
sol += "<tr><th></th><th></th><th></th><th></th><th></th><th></th><th></th>"
for d in all_rounds:
sol += f"<th>{d} - {getDateByIso[d].date()}</th>"
sol += "</tr>"
sol += "</thead>\n"
sol += "<tbody>\n"
for t in ucl_home:
sol += f"<tr><td>UCL</t><td>{t.id}</td><td>Pot {t.pot}</td><td>{t.country}</td><td>{t.name}</td><td>{t.shortname}</td><td>{team_pairing[t.id]}</td>"
for d in all_rounds:
if d in ucl_rounds:
if d in ucl_home[t]:
fontcolor = 'black'
bgcolor = 'lightsteelblue'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>H</td>"
elif d in ucl_away[t]:
fontcolor = 'black'
bgcolor = 'lightyellow'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>A</td>"
else:
sol += "<td></td>"
else:
sol += "<td style='background-color:lightgrey'></td>"
sol += "</tr>"
sol += "<tr style='background-color:lightgrey' ><th colspan='7'>UEL</th><th></th><th>1</th><th>2</th><th>3</th><th>4</th><th>5</th><th>6</th><th></th><th>7</th><th>8</th></tr>"
for t in uel_teams:
tname = getTeamByID[t].name
tshortname = getTeamByID[t].shortname
tcountry = getTeamByID[t].country
tpot = getTeamByID[t].pot
sol += f"<tr><td>UEL</t><td>{t}</td><td>Pot {tpot}</td><td>{tcountry}</td><td>{tname}</td><td>{tshortname}</td><td>{team_pairing[t]}</td>"
for d in all_rounds:
if d in uel_rounds:
if (d,t) in home_dict.keys():
fontcolor = 'black'
bgcolor = 'lightsteelblue'
if (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{home_dict[(d,t)]}</td>"
elif (d,t) in away_dict.keys():
fontcolor = 'black'
bgcolor = 'lightyellow'
if (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{away_dict[(d,t)]}</td>"
elif (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{viol_dict[(d,t)]}</td>"
else:
sol += "<td></td>"
else:
sol += "<td style='background-color:lightgrey'></td>"
sol += "</tr>"
sol += "<tr style='background-color:lightgrey'><th colspan='7'>UECL</th><th></th><th></th><th>1</th><th>2</th><th>3</th><th>4</th><th>5</th><th>6</th><th></th><th></th></tr>"
for t in uecl_teams:
tname = getTeamByID[t].name
tshortname = getTeamByID[t].shortname
tcountry = getTeamByID[t].country
tpot = getTeamByID[t].pot
sol += f"<tr><td>UECL</t><td>{t}</td><td>Pot {tpot}</td><td>{tcountry}</td><td>{tname}</td><td>{tshortname}</td><td>{team_pairing[t]}</td>"
for d in all_rounds:
if d in uecl_rounds:
# if (d,t) in viol_dict.keys():
# fontcolor = 'white'
# bgcolor = 'darkred'
# sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{viol_dict[(d,t)]}</td>"
if (d,t) in home_dict.keys():
fontcolor = 'black'
bgcolor = 'lightsteelblue'
if (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{home_dict[(d,t)]}</td>"
elif (d,t) in away_dict.keys():
fontcolor = 'black'
bgcolor = 'lightyellow'
if (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{away_dict[(d,t)]}</td>"
elif (d,t) in viol_dict.keys():
fontcolor = 'white'
bgcolor = 'darkred'
sol += f"<td style='min-width:80px;background-color:{bgcolor};color:{fontcolor}'>{viol_dict[(d,t)]}</td>"
else:
sol += "<td></td>"
else:
sol += "<td style='background-color:lightgrey'></td>"
sol += "</tr>"
sol += "</tbody>\n"
sol += "</table>\n"
with open(f'ueluecl24_debug.html', 'w') as f:
f.write(sol)
# %%

7636
uefa/scripts/uefa24_research.py Executable file

File diff suppressed because one or more lines are too long

208
uefa/scripts/uefa24_simulator.py Executable file
View File

@ -0,0 +1,208 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
# settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
settings.DATABASES['default']['HOST'] = '0.0.0.0'
settings.DATABASES['default']['PORT'] = '5432'
settings.DATABASES['default']['USER'] = 'postgres'
settings.DATABASES['default']['PASSWORD'] = 'secret123'
settings.DATABASES['default']['NAME'] = 'mypgsqldb'
settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
settings.DATABASES['default']['AUTOCOMMIT'] = True
settings.DATABASES['default']['CONN_MAX_AGE'] = 0
settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from scheduler.models import *
import pulp
from pulp import lpSum, value, XPRESS, GUROBI, PULP_CBC_CMD
from django.db.models import Q
from django.template.loader import render_to_string
from qualifiers.models import *
from common.models import GlobalTeam, GlobalCountry
from scheduler.models import Season, Scenario, Team, DayObj, CountryClash, Country
from qualifiers.draws import groupTeams, optimize_inversions4
from scheduler.solver.optimizer import optimize_2phases
from scheduler.solver.tasks.optimize import optimize
from draws.solver.optimize_draws import ucl24_ha_matrix, ucl24_opponent_matrix
from django.template.loader import render_to_string
from django.core.files.storage import FileSystemStorage
from django.utils.translation import gettext_lazy as _
# from gurobipy import *
import pulp
from pulp import lpSum, value, XPRESS_PY, XPRESS, GUROBI, PULP_CBC_CMD
from math import sqrt,pow,sin,cos,atan2,pi, ceil
from collections import defaultdict
import timeit
import datetime
import operator
import random
import time
import copy
# from os import dup, dup2, close, path
import os
from importlib import import_module
import builtins as __builtin__
import logging
import networkx as nx
import json
import string
import hashlib
from scheduler.models import *
from leagues.celery import celery, TASK_TIME_LIMIT
from leagues.settings import PULP_FOLDER
from scheduler.helpers import serialize_scenario, report_solverstatus
from scheduler.solver.functions import *
from scheduler.solver.tasks.optimize_localsearch import smartNeighbor
from scheduler.solver.tasks.optimize_submodels import ucl24_basicmodell, ueluecl24_basicmodell, ueluecl24_basicmodell_v2
from scheduler.helpers import copy_scenario
from draws.solver.optimize_draws import ucl24_ha_matrix
# from research.learners import AttendanceLearner
from sklearn.model_selection import train_test_split
from sklearn.ensemble import RandomForestRegressor
from sklearn.ensemble import GradientBoostingRegressor
import random
import time
import json
import csv
import networkx as nx
import matplotlib.pyplot as plt
from datetime import timedelta
from django.contrib.sessions.models import Session
def getVal(v):
if type(v) == int :
return v
else:
return v.value()
# basescenario = Scenario.objects.get(id=9306)
basescenario = Scenario.objects.get(id=9279)
# scenario = Scenario.objects.get(id=9308)
s2 = basescenario.id
user_name = 'md'
user_is_staff = True
runMode = 'New'
localsearch_time = 60
RUN_ENV = 'local'
SOLVER = 'xpress'
# %%
Scenario.objects.filter(season=basescenario.season,name__contains="Copy of BaseScenario").delete()
season = basescenario.season
print("START SIMULATION")
for counter in range(1,50):
name = f"Copy of BaseScenario {counter:03d}"
scenario = copy_scenario(basescenario, name=name, comment="")
print(f"COPY SCENARIO {name}")
scenario.last_modified = timezone.now()
scenario.last_modified_by = None
scenario.save()
# %%
# print("RANDOM DRAW")
# GameRequirement.objects.filter(scenario=scenario).delete()
# if season.optimizationParameters == 'UCL24':
# ucl24_ha_matrix(scenario.id)
# elif season.optimizationParameters == "UEL24":
# ucl24_ha_matrix(scenario.id,"UEL")
# ucl24_opponent_matrix(scenario,"UECL")
# print("DONE")
# %%
# # UPDATE TOPGAMES
# encgroups = EncGroup.objects.filter(scenario=scenario)
# Encounter.objects.filter(scenario=scenario).delete()
# for game in GameRequirement.objects.filter(scenario=scenario):
# if game.team1.attractivity >= 4 or game.team2.attractivity >= 4:
# if game.team1.attractivity >= 4 and game.team2.attractivity >= 4:
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="Top Games"))
# elif game.team1.attractivity >= 4:
# if game.team1.countryObj.shortname == "ENG":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="England top games"))
# if game.team1.countryObj.shortname == "FRA":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="France top games"))
# if game.team1.countryObj.shortname == "GER":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="German top games"))
# if game.team1.countryObj.shortname == "ITA":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="Italian top games"))
# if game.team1.countryObj.shortname == "ESP":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="Spain top games"))
# elif game.team2.attractivity >= 4:
# if game.team2.countryObj.shortname == "ENG":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="England top games"))
# if game.team2.countryObj.shortname == "FRA":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="France top games"))
# if game.team2.countryObj.shortname == "GER":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="German top games"))
# if game.team2.countryObj.shortname == "ITA":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="Italian top games"))
# if game.team2.countryObj.shortname == "ESP":
# enc = Encounter(scenario=scenario,encounterGroup=encgroups.get(name="Spain top games"))
# enc.save()
# enc.homeTeams.add(game.team1)
# enc.awayTeams.add(game.team2)
print("STARTING OPTIMIZATION")
try:
sol,kpis = optimize(task=None,s2=scenario.id, user_name=user_name, user_is_staff=user_is_staff,
runMode='New', localsearch_time=0, RUN_ENV=RUN_ENV, solver=SOLVER)
print("########################################")
print("AFTER NEW RUN")
print(kpis)
print("########################################")
sol,kpis = optimize(task=None,s2=scenario.id, user_name=user_name, user_is_staff=user_is_staff,
runMode='Improve', localsearch_time=localsearch_time, RUN_ENV=RUN_ENV, solver=SOLVER)
print("########################################")
print("AFTER IMPROVE")
print(kpis)
print("########################################")
except:
print("\t\tERROR")
pass

220
uefa/scripts/uefa_ucl24_seeder.py Executable file
View File

@ -0,0 +1,220 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
# settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
# settings.DATABASES['default']['HOST'] = '0.0.0.0'
# settings.DATABASES['default']['PORT'] = '5432'
# settings.DATABASES['default']['USER'] = 'postgres'
# settings.DATABASES['default']['PASSWORD'] = 'secret123'
# settings.DATABASES['default']['NAME'] = 'mypgsqldb'
# settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
# settings.DATABASES['default']['AUTOCOMMIT'] = True
# settings.DATABASES['default']['CONN_MAX_AGE'] = 0
# settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
# settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from django.shortcuts import HttpResponseRedirect
from django.http import HttpResponse, JsonResponse
from django.utils import timezone
from django.urls import reverse
from django.core.files.storage import FileSystemStorage
from django.core.mail import send_mail
from django_tex.shortcuts import render_to_pdf
from celery.result import AsyncResult
import googlemaps
import timeit
import random
import json
import builtins as __builtin__
import csv
from leagues.celery import celery
from leagues.settings import EMAIL_DEFAULT_FROM, EMAIL_DEFAULT_TO
from leagues.settings import RUN_ENV, INSTANCE, DEBUG
from common.tasks import log_telegram
from common.functions import *
from scheduler.models import *
from scheduler.helpers import *
from scheduler.widgets import widget_context_kpis
from scheduler.solver.optimizer import optimize_2phases, optimize_sequentially
import scheduler.solver.optimizer as so
from draws.solver import optimize_draws
import time as timer
from qualifiers.helpers import import_globals
# %%
scenario = Scenario.objects.get(id=7)
# import_globals(scenario.season.id)
# teams = scenario.season.scheduler_teams.all()
# %%
new_teams = []
new_teams.append((1, "Manchester City FC (ENG)", 145.000, "Pot 1",5,4))
new_teams.append((2, "FC Bayern München (GER)", 136.000, "Pot 1",5,5))
new_teams.append((3, "Liverpool FC (ENG)", 123.000, "Pot 1",5,5))
new_teams.append((4, "Real Madrid CF (ESP)", 121.000, "Pot 1",5,5))
new_teams.append((5, "Paris Saint-Germain (FRA)", 112.000, "Pot 1",5,5))
new_teams.append((6, "Manchester United FC (ENG)", 104.000, "Pot 1",5,5))
new_teams.append((7, "FC Barcelona (ESP)", 98.000, "Pot 1",5,5))
new_teams.append((8, "FC Internazionale Milano (ITA)", 96.000, "Pot 1",4,5))
new_teams.append((9, "Sevilla FC (ESP)", 91.000, "Pot 1",3,4))
new_teams.append((10, "Borussia Dortmund (GER)", 86.000, "Pot 2",4,4))
new_teams.append((11, "Club Atlético de Madrid (ESP)", 85.000, "Pot 2",4,4))
new_teams.append((12, "RB Leipzig (GER)", 84.000, "Pot 2",3,3))
new_teams.append((13, "SL Benfica (POR)", 82.000, "Pot 2",2,5))
new_teams.append((14, "SSC Napoli (ITA)", 81.000, "Pot 2",3,4))
new_teams.append((15, "FC Porto (POR)", 81.000, "Pot 2",3,5))
new_teams.append((16, "Arsenal FC (ENG)", 76.000, "Pot 2",4,4))
new_teams.append((17, "FC Shakhtar Donetsk (UKR)", 63.000, "Pot 2",1,5))
new_teams.append((18, "FC Salzburg (AUT)", 59.000, "Pot 2",2,5))
new_teams.append((19, "Atalanta BC (ITA)", 55.500, "Pot 3",2,3))
new_teams.append((20, "Feyenoord (NED)", 51.000, "Pot 3",2,4))
new_teams.append((21, "AC Milan (ITA)", 50.000, "Pot 3",3,5))
new_teams.append((22, "SC Braga (POR)", 44.000, "Pot 3",2,3))
new_teams.append((23, "PSV Eindhoven (NED)", 43.000, "Pot 3",2,4))
new_teams.append((24, "S.S. Lazio (ITA)", 42.000, "Pot 3",2,3))
new_teams.append((25, "FK Crvena zvezda (SRB)", 42.000, "Pot 3",1,5))
new_teams.append((26, "F.C. Copenhagen (DEN)", 40.500, "Pot 3",1,4))
new_teams.append((27, "BSC Young Boys (SUI)", 34.500, "Pot 3",1,4))
new_teams.append((28, "Real Sociedad de Fútbol (ESP)", 33.000, "Pot 4",2,3))
new_teams.append((29, "Olympique de Marseille (FRA)", 33.000, "Pot 4",3,4))
new_teams.append((30, "Galatasaray A.Ş. (TUR)", 31.500, "Pot 4",1,5))
new_teams.append((31, "Celtic FC (SCO)", 31.000, "Pot 4",2,3))
new_teams.append((32, "Qarabağ FK (AZE)", 25.000, "Pot 4",1,5))
new_teams.append((33, "Newcastle United FC (ENG)", 21.914, "Pot 4",3,3))
new_teams.append((34, "1. FC Union Berlin (GER)", 17.000, "Pot 4",2,3))
new_teams.append((35, "R. Antwerp FC (BEL)", 17.000, "Pot 4",3,3))
new_teams.append((36, "RC Lens (FRA)", 12.232, "Pot 4",2,3))
CET_minus_1 = ['ENG','POR','SCO']
CET_plus_1 = ['TUR','AZE','ISR','UKR']
# %%
for i in range(1,6):
Conference.objects.get_or_create(scenario=scenario,name=f"Global Coeff {i}")
Conference.objects.get_or_create(scenario=scenario,name=f"Domestic Coeff {i}")
Conference.objects.get_or_create(scenario=scenario,name="CET")
Conference.objects.get_or_create(scenario=scenario,name="CET-1")
Conference.objects.get_or_create(scenario=scenario,name="CET+1")
for conf in Conference.objects.filter(scenario=scenario).exclude(name__in=['HARD Constraints','SOFT Constraints']):
conf.teams.clear()
conf.collapseInView = True
conf.save()
Team.objects.filter(season=scenario.season).update(active=False)
for t in new_teams:
team_name = t[1].split('(')[0].strip()
team_country = t[1].split('(')[1].split(')')[0].strip()
# abbreviation = t[2]
global_coeff = t[4]
domestic_coeff = t[5]
pot = int(t[3].split(' ')[1].strip())
pos = int(t[0])
competition = "UCL"
teamObj = Team.objects.filter(season=scenario.season,name=team_name)
if teamObj:
pass
else:
print(t,"->", team_name)
gteam = GlobalTeam.objects.filter(name=team_name)
if gteam:
teamObj = Team.objects.create(season=scenario.season,
name=team_name,
attractivity=global_coeff+0.1*domestic_coeff,
position=pos,
pot=pot,
latitude=gteam.first().latitude,
longitude=gteam.first().longitude,
country=gteam.first().country,
active=True)
print("\tCreated team from global", team_name)
teamObj = Team.objects.filter(season=scenario.season,name=team_name)
else:
print("\tTeam not found", team_name)
continue
Conference.objects.filter(scenario=scenario,name=competition).first().teams.add(teamObj.first())
Conference.objects.filter(scenario=scenario,name=f"{t[3]}").first().teams.add(teamObj.first())
if global_coeff in range(1,6):
Conference.objects.filter(scenario=scenario,name=f"Global Coeff {global_coeff}").first().teams.add(teamObj.first())
if domestic_coeff in range(1,6):
Conference.objects.filter(scenario=scenario,name=f"Domestic Coeff {domestic_coeff}").first().teams.add(teamObj.first())
if team_country in CET_minus_1:
Conference.objects.filter(scenario=scenario,name="CET-1").first().teams.add(teamObj.first())
elif team_country in CET_plus_1:
Conference.objects.filter(scenario=scenario,name="CET+1").first().teams.add(teamObj.first())
else:
Conference.objects.filter(scenario=scenario,name="CET").first().teams.add(teamObj.first())
teamObj.update(active=True)
teamObj.update(attractivity=global_coeff+0.1*domestic_coeff)
teamObj.update(coefficient=5-pot)
teamObj.update(position=pos)
teamObj.update(pot=pot)
for conf in Conference.objects.filter(scenario=scenario):
for t in conf.teams.filter(active=False):
conf.teams.remove(t)
for haw in HAWish.objects.filter(scenario=scenario):
for t in haw.teams.filter(active=False):
haw.teams.remove(t)
for enc in EncWish.objects.filter(scenario=scenario):
for t in enc.teams1.filter(active=False):
enc.teams1.remove(t)
for t in enc.teams2.filter(active=False):
enc.teams1.remove(t)
for pair in Pairing.objects.filter(scenario=scenario):
if pair.team1.active==False or pair.team2.active==False:
pair.delete()
# %%

View File

@ -0,0 +1,190 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
# settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
# settings.DATABASES['default']['HOST'] = '0.0.0.0'
# settings.DATABASES['default']['PORT'] = '5432'
# settings.DATABASES['default']['USER'] = 'postgres'
# settings.DATABASES['default']['PASSWORD'] = 'secret123'
# settings.DATABASES['default']['NAME'] = 'mypgsqldb'
# settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
# settings.DATABASES['default']['AUTOCOMMIT'] = True
# settings.DATABASES['default']['CONN_MAX_AGE'] = 0
# settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
# settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from django.shortcuts import HttpResponseRedirect
from django.http import HttpResponse, JsonResponse
from django.utils import timezone
from django.urls import reverse
from django.core.files.storage import FileSystemStorage
from django.core.mail import send_mail
from django_tex.shortcuts import render_to_pdf
from celery.result import AsyncResult
import googlemaps
import timeit
import random
import json
import builtins as __builtin__
import csv
from leagues.celery import celery
from leagues.settings import EMAIL_DEFAULT_FROM, EMAIL_DEFAULT_TO
from leagues.settings import RUN_ENV, INSTANCE, DEBUG
from common.tasks import log_telegram
from common.functions import *
from scheduler.models import *
from scheduler.helpers import *
from scheduler.widgets import widget_context_kpis
from scheduler.solver.optimizer import optimize_2phases, optimize_sequentially
import scheduler.solver.optimizer as so
from draws.solver import optimize_draws
import time as timer
from qualifiers.helpers import import_globals
# %%
scenario = Scenario.objects.get(id=3)
# import_globals(scenario.season.id)
# teams = scenario.season.scheduler_teams.all()
# %%
new_teams = []
new_teams.append(("Pot 1", 1, "Tottenham Hotspur (ENG)", 80.000, 5,5 ))
new_teams.append(("Pot 1", 2, "Eintracht Frankfurt (GER)", 77.000, 5,5 ))
new_teams.append(("Pot 1", 3, "Club Brugge (BEL)", 54.000, 2,5 ))
new_teams.append(("Pot 1", 4, "FC Basel 1893 (SUI)", 53.000, 3,5 ))
new_teams.append(("Pot 1", 5, "KAA Gent (BEL)", 37.500, 1,4 ))
new_teams.append(("Pot 1", 6, "Fenerbahçe SK (TUR)", 30.000, 3,5 ))
new_teams.append(("Pot 2", 7, "AS Monaco FC (FRA)", 29.000, 4,5 ))
new_teams.append(("Pot 2", 8, "CFR 1907 Cluj (ROU)", 27.500, 1,5 ))
new_teams.append(("Pot 2", 9, "FC Midtjylland (DEN)", 25.500, 1,5 ))
new_teams.append(("Pot 2", 10, "PAOK FC (GRE)", 25.000, 1,3 ))
new_teams.append(("Pot 2", 11, "ŠK Slovan Bratislava (SVK)", 24.500, 1,5 ))
new_teams.append(("Pot 2", 12, "Maccabi Tel-Aviv FC (ISR)", 24.000, 1,5 ))
new_teams.append(("Pot 3", 13, "FC Viktoria Plzeň (CZE)", 22.000, 2,4 ))
new_teams.append(("Pot 3", 14, "PFC Ludogorets 1945 (BUL)", 21.000, 1,5 ))
new_teams.append(("Pot 3", 15, "FK Bodø/Glimt (NOR)", 20.000, 2,5 ))
new_teams.append(("Pot 3", 16, "CA Osasuna (ESP)", 18.599, 3,3 ))
new_teams.append(("Pot 3", 17, "KRC Genk (BEL)", 18.000, 1,4 ))
new_teams.append(("Pot 3", 18, "FC Bologna (ITA)", 16.385, 3,3 ))
new_teams.append(("Pot 4", 19, "FC Zorya Luhansk (UKR)", 16.000, 1,3 ))
new_teams.append(("Pot 4", 20, "FC Astana (KAZ)", 14.000, 1,5 ))
new_teams.append(("Pot 4", 21, "Beşiktaş (TUR)", 14.000, 3,5 ))
new_teams.append(("Pot 4", 22, "FK Žalgiris Vilnius (LTU)", 11.000, 1,5 ))
new_teams.append(("Pot 4", 23, "HJK Helsinki (FIN)", 11.000, 1,5 ))
new_teams.append(("Pot 4", 24, "FC Flora Tallinn (EST)", 10.500, 1,5 ))
new_teams.append(("Pot 5", 25, "Legia Warszawa (POL)", 11.000, 1,5 ))
new_teams.append(("Pot 5", 26, "FC Spartak Trnava (SVK)", 10.500, 1,4 ))
new_teams.append(("Pot 5", 27, "NK Olimpija Ljubljana (SVN)", 9.000, 1,5 ))
new_teams.append(("Pot 5", 28, "HŠK Zrinjski (BIH)", 8.500, 1,5 ))
new_teams.append(("Pot 5", 29, "Dnipro-1 (UKR)", 8.000, 1,3 ))
new_teams.append(("Pot 5", 30, "KÍ Klaksvík (FRO)", 8.000, 1,5 ))
new_teams.append(("Pot 6", 31, "Aberdeen FC (SCO)", 8.000, 2,3 ))
new_teams.append(("Pot 6", 32, "FK Čukarički (SRB)", 6.475, 1,5 ))
new_teams.append(("Pot 6", 33, "FC Lugano (SUI)", 6.335, 1,3 ))
new_teams.append(("Pot 6", 34, "Breidablik (ISL)", 6.000, 1,5 ))
new_teams.append(("Pot 6", 35, "FC Nordsjælland (DEN)", 5.565, 1,5 ))
new_teams.append(("Pot 6", 36, "Ballkani (KOS)", 3.000, 1,5 ))
CET_minus_1 = ['ENG','POR','SCO']
CET_plus_1 = ['TUR','AZE','ISR','UKR']
# %%
for conf in Conference.objects.filter(scenario=scenario).exclude(name__in=['HARD Constraints','SOFT Constraints']):
conf.teams.clear()
conf.collapseInView = True
conf.save()
Team.objects.filter(season=scenario.season).update(active=False)
for t in new_teams:
team_name = t[2].split('(')[0].strip()
team_country = t[2].split('(')[1].split(')')[0].strip()
global_coeff = t[4]
domestic_coeff = t[5]
pot = int(t[0].split(' ')[1].strip())
pos = int(t[1])
teamObj = Team.objects.filter(season=scenario.season,name=team_name)
if teamObj:
pass
else:
print(t,"->", team_name)
gteam = GlobalTeam.objects.filter(name=team_name)
if gteam:
new_t = Team.objects.create(season=scenario.season,
name=team_name,
attractivity=global_coeff,
position=pos,
pot=pot,
latitude=gteam.first().latitude,
longitude=gteam.first().longitude,
country=gteam.first().country,
active=True)
print("\tCreated team from global", team_name)
teamObj = Team.objects.filter(season=scenario.season,name=team_name)
else:
print("\tTeam not found", team_name)
continue
Conference.objects.filter(scenario=scenario,name="UECL").first().teams.add(teamObj.first())
Conference.objects.filter(scenario=scenario,name=t[0]).first().teams.add(teamObj.first())
# if global_coeff in [3,4,5]:
# Conference.objects.filter(scenario=scenario,name=f"Global Coeff {global_coeff}").first().teams.add(teamObj.first())
# if domestic_coeff in [3,5]:
# Conference.objects.filter(scenario=scenario,name=f"Domestic Coeff {domestic_coeff}").first().teams.add(teamObj.first())
if team_country in CET_minus_1:
Conference.objects.filter(scenario=scenario,name="CET-1").first().teams.add(teamObj.first())
elif team_country in CET_plus_1:
Conference.objects.filter(scenario=scenario,name="CET+1").first().teams.add(teamObj.first())
else:
Conference.objects.filter(scenario=scenario,name="CET").first().teams.add(teamObj.first())
teamObj.update(active=True)
teamObj.update(attractivity=global_coeff)
teamObj.update(position=pos)
teamObj.update(pot=pot)
# %%

232
uefa/scripts/uefa_uel24_seeder.py Executable file
View File

@ -0,0 +1,232 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
# settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
# settings.DATABASES['default']['HOST'] = '0.0.0.0'
# settings.DATABASES['default']['PORT'] = '5432'
# settings.DATABASES['default']['USER'] = 'postgres'
# settings.DATABASES['default']['PASSWORD'] = 'secret123'
# settings.DATABASES['default']['NAME'] = 'mypgsqldb'
# settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
# settings.DATABASES['default']['AUTOCOMMIT'] = True
# settings.DATABASES['default']['CONN_MAX_AGE'] = 0
# settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
# settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from django.shortcuts import HttpResponseRedirect
from django.http import HttpResponse, JsonResponse
from django.utils import timezone
from django.urls import reverse
from django.core.files.storage import FileSystemStorage
from django.core.mail import send_mail
from django_tex.shortcuts import render_to_pdf
from celery.result import AsyncResult
import googlemaps
import timeit
import random
import json
import builtins as __builtin__
import csv
from leagues.celery import celery
from leagues.settings import EMAIL_DEFAULT_FROM, EMAIL_DEFAULT_TO
from leagues.settings import RUN_ENV, INSTANCE, DEBUG
from common.tasks import log_telegram
from common.functions import *
from scheduler.models import *
from scheduler.helpers import *
from scheduler.widgets import widget_context_kpis
from scheduler.solver.optimizer import optimize_2phases, optimize_sequentially
import scheduler.solver.optimizer as so
from draws.solver import optimize_draws
import time as timer
from qualifiers.helpers import import_globals
# %%
scenario = Scenario.objects.get(id=4)
# import_globals(scenario.season.id)
# teams = scenario.season.scheduler_teams.all()
# %%
new_teams = []
new_teams.append(("Pot 1",1, "Roma", "AS Roma (ITA) ", 97.000, 5,5, "UEL"))
new_teams.append(("Pot 1",2, "Ajax", "AFC Ajax (NED)", 89.000, 5,5 , "UEL"))
new_teams.append(("Pot 1",3, "Villa", "Villarreal CF (ESP)", 82.000, 5,5 , "UEL"))
new_teams.append(("Pot 1",4, "Bayer", "Bayer 04 Leverkusen (GER)", 72.000, 4,4 , "UEL"))
new_teams.append(("Pot 1",5, "GNK", "GNK Dinamo (CRO) ", 55.000, 2,5 , "UEL"))
new_teams.append(("Pot 1",6, "Ranger", "Rangers FC (SCO)", 54.000, 4,5 , "UEL"))
new_teams.append(("Pot 1",7, "Sporti", "Sporting Clube de Portugal (POR)", 52.500, 4,5 , "UEL"))
new_teams.append(("Pot 1",8, "Slavia", "SK Slavia Praha (CZE)", 52.000, 2,5 , "UEL"))
new_teams.append(("Pot 1",9, "WestHam", "West Ham United FC (ENG)", 50.000, 4,4 , "UEL"))
new_teams.append(("Pot 2",10, "Alkmaa", "AZ Alkmaar (NED)", 47.500, 2,3 , "UEL"))
new_teams.append(("Pot 2",11, "Stade", "Stade Rennais FC (FRA) ", 44.000, 3,5 , "UEL"))
new_teams.append(("Pot 2",12, "Olymp", "Olympiacos FC (GRE)", 39.000, 2,5 , "UEL"))
new_teams.append(("Pot 2",13, "Betis", "Real Betis Balompié (ESP)", 37.000, 3,4 , "UEL"))
new_teams.append(("Pot 2",14, "Linz", "LASK Linz (AUT)", 36.000, 1,4 , "UEL"))
new_teams.append(("Pot 2",15, "Kyiv", "FC Dynamo Kyiv (UKR)", 35.000, 3,5 , "UEL"))
new_teams.append(("Pot 2",16, "Lille", "LOSC Lille (FRA)", 30.000, 3,4 , "UEL"))
new_teams.append(("Pot 2",17, "Feren", "Ferencvárosi TC (HUN)", 27.000, 1,5 , "UEL"))
new_teams.append(("Pot 2",18, "Molde", "Molde FK (NOR)", 24.000, 1,5 , "UEL"))
new_teams.append(("Pot 3",19, "Bright", "Brighton & Hove Albion (ENG)", 21.914, 3,3 , "UEL"))
new_teams.append(("Pot 3",20, "Aston", "Aston Villa FC (ENG)", 21.914, 4,4 , "UEL"))
new_teams.append(("Pot 3",21, "Fiore", "ACF Fiorentina (ITA)", 20.000, 4,4 , "UEL"))
new_teams.append(("Pot 3",22, "Tiras", "FC Sheriff Tiraspol (MDA) ", 19.500, 1,5 , "UEL"))
new_teams.append(("Pot 3",23, "St.Gil", "Union Saint-Gilloise (BEL)", 19.000, 1,4 , "UEL"))
new_teams.append(("Pot 3",24, "Rapid", "SK Rapid Wien (AUT)", 18.500, 2,5 , "UEL"))
new_teams.append(("Pot 3",25, "Freib", "SC Freiburg (GER)", 16.496, 4,4 , "UEL"))
new_teams.append(("Pot 3",26, "Sparta", "AC Sparta Praha (CZE)", 14.000, 2,5 , "UEL"))
new_teams.append(("Pot 3",27, "Haifa", "Maccabi Haifa FC (ISR)", 13.000, 2,5 , "UEL"))
new_teams.append(("Pot 4",28, "Sturm", "SK Sturm Graz (AUT)", 12.500, 1,5 , "UEL"))
new_teams.append(("Pot 4",29, "Toul", "Toulouse FC (FRA)", 12.232, 3,4 , "UEL"))
new_teams.append(("Pot 4",30, "Athen", "AEK Athens FC (GRE)", 11.000, 1,4 , "UEL"))
new_teams.append(("Pot 4",31, "Topola", "FK TSC Bačka Topola (SRB)", 6.475, 1,5 , "UEL"))
new_teams.append(("Pot 4",32, "Serve", "Servette FC (SUI) ", 6.335, 1,4 , "UEL"))
new_teams.append(("Pot 4",33, "Panat", "Panathinaikos FC (GRE) ", 5.045, 1,5 , "UEL"))
new_teams.append(("Pot 4",34, "Raków", "Raków Czestochowa (POL) ", 5.000, 1,3 , "UEL"))
new_teams.append(("Pot 4",35, "Aris", "Aris Limassol FC (CYP)", 4.895, 1,5 , "UEL"))
new_teams.append(("Pot 4",36, "Häcke", "BK Häcken (SWE)", 4.750, 1,5 , "UEL"))
new_teams.append(("Pot 1", 1, "Hotsp", "Tottenham Hotspur (ENG)", 80.000, 5,5 , "UECL"))
new_teams.append(("Pot 1", 2, "Frank", "Eintracht Frankfurt (GER)", 77.000, 5,5 , "UECL"))
new_teams.append(("Pot 1", 3, "Brugg", "Club Brugge (BEL)", 54.000, 2,5 , "UECL"))
new_teams.append(("Pot 1", 4, "Basel", "FC Basel 1893 (SUI)", 53.000, 3,5 , "UECL"))
new_teams.append(("Pot 1", 5, "Gent", "KAA Gent (BEL)", 37.500, 1,4 , "UECL"))
new_teams.append(("Pot 1", 6, "Fener", "Fenerbahçe SK (TUR)", 30.000, 3,5 , "UECL"))
new_teams.append(("Pot 2", 7, "Monac", "AS Monaco FC (FRA)", 29.000, 4,5 , "UECL"))
new_teams.append(("Pot 2", 8, "Cluj", "CFR 1907 Cluj (ROU)", 27.500, 1,5 , "UECL"))
new_teams.append(("Pot 2", 9, "Midty", "FC Midtjylland (DEN)", 25.500, 1,5 , "UECL"))
new_teams.append(("Pot 2", 10, "PAOK", "PAOK FC (GRE)", 25.000, 1,3 , "UECL"))
new_teams.append(("Pot 2", 11, "Brati", "ŠK Slovan Bratislava (SVK)", 24.500, 1,5 , "UECL"))
new_teams.append(("Pot 2", 12, "Macca", "Maccabi Tel-Aviv FC (ISR)", 24.000, 1,5 , "UECL"))
new_teams.append(("Pot 3", 13, "Plzeň", "FC Viktoria Plzeň (CZE)", 22.000, 2,4 , "UECL"))
new_teams.append(("Pot 3", 14, "Ludog", "PFC Ludogorets 1945 (BUL)", 21.000, 1,5 , "UECL"))
new_teams.append(("Pot 3", 15, "Glimt", "FK Bodø/Glimt (NOR)", 20.000, 2,5 , "UECL"))
new_teams.append(("Pot 3", 16, "Osaun", "CA Osasuna (ESP)", 18.599, 3,3 , "UECL"))
new_teams.append(("Pot 3", 17, "Genk", "KRC Genk (BEL)", 18.000, 1,4 , "UECL"))
new_teams.append(("Pot 3", 18, "Bolog", "FC Bologna (ITA)", 16.385, 3,3 , "UECL"))
new_teams.append(("Pot 4", 19, "Luhan", "FC Zorya Luhansk (UKR)", 16.000, 1,3 , "UECL"))
new_teams.append(("Pot 4", 20, "Astana", "FC Astana (KAZ)", 14.000, 1,5 , "UECL"))
new_teams.append(("Pot 4", 21, "Beşikt", "Beşiktaş (TUR)", 14.000, 3,5 , "UECL"))
new_teams.append(("Pot 4", 22, "Vilni", "FK Žalgiris Vilnius (LTU)", 11.000, 1,5 , "UECL"))
new_teams.append(("Pot 4", 23, "Helsi", "HJK Helsinki (FIN)", 11.000, 1,5 , "UECL"))
new_teams.append(("Pot 4", 24, "Flora", "FC Flora Tallinn (EST)", 10.500, 1,5 , "UECL"))
new_teams.append(("Pot 5", 25, "Legia", "Legia Warszawa (POL)", 11.000, 1,5 , "UECL"))
new_teams.append(("Pot 5", 26, "Trna", "FC Spartak Trnava (SVK)", 10.500, 1,4 , "UECL"))
new_teams.append(("Pot 5", 27, "Ljubl", "NK Olimpija Ljubljana (SVN)", 9.000, 1,5 , "UECL"))
new_teams.append(("Pot 5", 28, "Zrinj", "HŠK Zrinjski (BIH)", 8.500, 1,5 , "UECL"))
new_teams.append(("Pot 5", 29, "Dnipr", "Dnipro-1 (UKR)", 8.000, 1,3 , "UECL"))
new_teams.append(("Pot 5", 30, "Klaks", "KÍ Klaksvík (FRO)", 8.000, 1,5 , "UECL"))
new_teams.append(("Pot 6", 31, "Aberd", "Aberdeen FC (SCO)", 8.000, 2,3 , "UECL"))
new_teams.append(("Pot 6", 32, "Čukar", "FK Čukarički (SRB)", 6.475, 1,5 , "UECL"))
new_teams.append(("Pot 6", 33, "Lugano", "FC Lugano (SUI)", 6.335, 1,3 , "UECL"))
new_teams.append(("Pot 6", 34, "Breida", "Breidablik (ISL)", 6.000, 1,5 , "UECL"))
new_teams.append(("Pot 6", 35, "Nordsj", "FC Nordsjælland (DEN)", 5.565, 1,5 , "UECL"))
new_teams.append(("Pot 6", 36, "Ballk", "Ballkani (KOS)", 3.000, 1,5 , "UECL"))
CET_minus_1 = ['ENG','POR','SCO']
CET_plus_1 = ['TUR','AZE','ISR','UKR']
# %%
for conf in Conference.objects.filter(scenario=scenario):
conf.teams.clear()
conf.collapseInView = True
conf.save()
Team.objects.filter(season=scenario.season).update(active=False)
for t in new_teams:
team_name = t[3].split('(')[0].strip()
team_country = t[3].split('(')[1].split(')')[0].strip()
abbreviation = t[4]
global_coeff = t[5]
domestic_coeff = t[6]
pot = int(t[0].split(' ')[1].strip())
pos = int(t[1])
competition = t[7]
teamObj = Team.objects.filter(season=scenario.season,name=team_name)
if teamObj:
pass
else:
print(t,"->", team_name)
gteam = GlobalTeam.objects.filter(name=team_name)
if gteam:
teamObj = Team.objects.create(season=scenario.season,
name=team_name,
attractivity=global_coeff+0.1*domestic_coeff,
position=pos,
pot=pot,
latitude=gteam.first().latitude,
longitude=gteam.first().longitude,
country=gteam.first().country,
active=True)
print("\tCreated team from global", team_name)
teamObj = Team.objects.filter(season=scenario.season,name=team_name)
else:
print("\tTeam not found", team_name)
continue
Conference.objects.filter(scenario=scenario,name=competition).first().teams.add(teamObj.first())
Conference.objects.filter(scenario=scenario,name=f"{competition}-{t[0]}").first().teams.add(teamObj.first())
# if global_coeff in [3,4,5]:
# Conference.objects.filter(scenario=scenario,name=f"Global Coeff {global_coeff}").first().teams.add(teamObj.first())
# if domestic_coeff in [3,5]:
# Conference.objects.filter(scenario=scenario,name=f"Domestic Coeff {domestic_coeff}").first().teams.add(teamObj.first())
if team_country in CET_minus_1:
Conference.objects.filter(scenario=scenario,name="CET-1").first().teams.add(teamObj.first())
elif team_country in CET_plus_1:
Conference.objects.filter(scenario=scenario,name="CET+1").first().teams.add(teamObj.first())
else:
Conference.objects.filter(scenario=scenario,name="CET").first().teams.add(teamObj.first())
teamObj.update(active=True)
teamObj.update(attractivity=global_coeff)
teamObj.update(position=pos)
teamObj.update(pot=pot)
if teamObj.first().shortname == "":
teamObj.update(shortname=abbreviation)
# %%

View File

@ -0,0 +1,259 @@
# %%
PROJECT_PATH = '/home/md/Work/ligalytics/leagues_stable/'
import os, sys
sys.path.insert(0, PROJECT_PATH)
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "leagues.settings")
os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"
from leagues import settings
settings.DATABASES['default']['NAME'] = PROJECT_PATH+'/db.sqlite3'
# settings.DATABASES['default']['ENGINE'] = 'django.db.backends.postgresql_psycopg2'
# settings.DATABASES['default']['HOST'] = '0.0.0.0'
# settings.DATABASES['default']['PORT'] = '5432'
# settings.DATABASES['default']['USER'] = 'postgres'
# settings.DATABASES['default']['PASSWORD'] = 'secret123'
# settings.DATABASES['default']['NAME'] = 'mypgsqldb'
# settings.DATABASES['default']['ATOMIC_REQUESTS'] = False
# settings.DATABASES['default']['AUTOCOMMIT'] = True
# settings.DATABASES['default']['CONN_MAX_AGE'] = 0
# settings.DATABASES['default']['CONN_HEALTH_CHECKS'] = False
# settings.DATABASES['default']['OPTIONS'] = {}
os.environ["XPRESSDIR"] = "/opt/xpressmp"
os.environ["XPRESS"] = "/opt/xpressmp/bin"
os.environ["LD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["DYLD_LIBRARY_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["SHLIB_PATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["LIBPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["PYTHONPATH"] = os.environ["XPRESSDIR"] + "/lib"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprs.jar"
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprb.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["CLASSPATH"] = os.environ["XPRESSDIR"] + "/lib/xprm.jar" + os.pathsep + os.environ["CLASSPATH"]
os.environ["PATH"] = os.environ["XPRESSDIR"] + "/bin" + os.pathsep + os.environ["PATH"]
import django
django.setup()
from django.shortcuts import HttpResponseRedirect
from django.http import HttpResponse, JsonResponse
from django.utils import timezone
from django.urls import reverse
from django.core.files.storage import FileSystemStorage
from django.core.mail import send_mail
from django_tex.shortcuts import render_to_pdf
from celery.result import AsyncResult
import googlemaps
import timeit
import random
import json
import builtins as __builtin__
import csv
from leagues.celery import celery
from leagues.settings import EMAIL_DEFAULT_FROM, EMAIL_DEFAULT_TO
from leagues.settings import RUN_ENV, INSTANCE, DEBUG
from common.tasks import log_telegram
from common.functions import *
from scheduler.models import *
from scheduler.helpers import *
from scheduler.widgets import widget_context_kpis
from scheduler.solver.optimizer import optimize_2phases, optimize_sequentially
import scheduler.solver.optimizer as so
from draws.solver import optimize_draws
import time as timer
from qualifiers.helpers import import_globals
# %%
scenario = Scenario.objects.get(id=9)
# import_globals(scenario.season.id)
# teams = scenario.season.scheduler_teams.all()
# %%
new_teams = []
new_teams.append(("Pot 1",1, "Roma", "AS Roma (ITA) ", 97.000, 5,5, "UEL"))
new_teams.append(("Pot 1",2, "Ajax", "AFC Ajax (NED)", 89.000, 5,5 , "UEL"))
new_teams.append(("Pot 1",3, "Villa", "Villarreal CF (ESP)", 82.000, 5,5 , "UEL"))
new_teams.append(("Pot 1",4, "Bayer", "Bayer 04 Leverkusen (GER)", 72.000, 4,4 , "UEL"))
new_teams.append(("Pot 1",5, "GNK", "GNK Dinamo (CRO) ", 55.000, 2,5 , "UEL"))
new_teams.append(("Pot 1",6, "Ranger", "Rangers FC (SCO)", 54.000, 4,5 , "UEL"))
new_teams.append(("Pot 1",7, "Sporti", "Sporting Clube de Portugal (POR)", 52.500, 4,5 , "UEL"))
new_teams.append(("Pot 1",8, "Slavia", "SK Slavia Praha (CZE)", 52.000, 2,5 , "UEL"))
new_teams.append(("Pot 1",9, "WestHam", "West Ham United FC (ENG)", 50.000, 4,4 , "UEL"))
new_teams.append(("Pot 2",10, "Alkmaa", "AZ Alkmaar (NED)", 47.500, 2,3 , "UEL"))
new_teams.append(("Pot 2",11, "Stade", "Stade Rennais FC (FRA) ", 44.000, 3,5 , "UEL"))
new_teams.append(("Pot 2",12, "Olymp", "Olympiacos FC (GRE)", 39.000, 2,5 , "UEL"))
new_teams.append(("Pot 2",13, "Betis", "Real Betis Balompié (ESP)", 37.000, 3,4 , "UEL"))
new_teams.append(("Pot 2",14, "Linz", "LASK Linz (AUT)", 36.000, 1,4 , "UEL"))
new_teams.append(("Pot 2",15, "Kyiv", "FC Dynamo Kyiv (UKR)", 35.000, 3,5 , "UEL"))
new_teams.append(("Pot 2",16, "Lille", "LOSC Lille (FRA)", 30.000, 3,4 , "UEL"))
new_teams.append(("Pot 2",17, "Feren", "Ferencvárosi TC (HUN)", 27.000, 1,5 , "UEL"))
new_teams.append(("Pot 2",18, "Molde", "Molde FK (NOR)", 24.000, 1,5 , "UEL"))
new_teams.append(("Pot 3",19, "Bright", "Brighton & Hove Albion (ENG)", 21.914, 3,3 , "UEL"))
new_teams.append(("Pot 3",20, "Aston", "Aston Villa FC (ENG)", 21.914, 4,4 , "UEL"))
new_teams.append(("Pot 3",21, "Fiore", "ACF Fiorentina (ITA)", 20.000, 4,4 , "UEL"))
new_teams.append(("Pot 3",22, "Tiras", "FC Sheriff Tiraspol (MDA) ", 19.500, 1,5 , "UEL"))
new_teams.append(("Pot 3",23, "St.Gil", "Union Saint-Gilloise (BEL)", 19.000, 1,4 , "UEL"))
new_teams.append(("Pot 3",24, "Rapid", "SK Rapid Wien (AUT)", 18.500, 2,5 , "UEL"))
new_teams.append(("Pot 3",25, "Freib", "SC Freiburg (GER)", 16.496, 4,4 , "UEL"))
new_teams.append(("Pot 3",26, "Sparta", "AC Sparta Praha (CZE)", 14.000, 2,5 , "UEL"))
new_teams.append(("Pot 3",27, "Haifa", "Maccabi Haifa FC (ISR)", 13.000, 2,5 , "UEL"))
new_teams.append(("Pot 4",28, "Sturm", "SK Sturm Graz (AUT)", 12.500, 1,5 , "UEL"))
new_teams.append(("Pot 4",29, "Toul", "Toulouse FC (FRA)", 12.232, 3,4 , "UEL"))
new_teams.append(("Pot 4",30, "Athen", "AEK Athens FC (GRE)", 11.000, 1,4 , "UEL"))
new_teams.append(("Pot 4",31, "Topola", "FK TSC Bačka Topola (SRB)", 6.475, 1,5 , "UEL"))
new_teams.append(("Pot 4",32, "Serve", "Servette FC (SUI) ", 6.335, 1,4 , "UEL"))
new_teams.append(("Pot 4",33, "Panat", "Panathinaikos FC (GRE) ", 5.045, 1,5 , "UEL"))
new_teams.append(("Pot 4",34, "Raków", "Raków Czestochowa (POL) ", 5.000, 1,3 , "UEL"))
new_teams.append(("Pot 4",35, "Aris", "Aris Limassol FC (CYP)", 4.895, 1,5 , "UEL"))
new_teams.append(("Pot 4",36, "Häcke", "BK Häcken (SWE)", 4.750, 1,5 , "UEL"))
new_teams.append(("Pot 1", 1, "Hotsp", "Tottenham Hotspur (ENG)", 80.000, 5,5 , "UECL"))
new_teams.append(("Pot 1", 2, "Frank", "Eintracht Frankfurt (GER)", 77.000, 5,5 , "UECL"))
new_teams.append(("Pot 1", 3, "Brugg", "Club Brugge (BEL)", 54.000, 2,5 , "UECL"))
new_teams.append(("Pot 1", 4, "Basel", "FC Basel 1893 (SUI)", 53.000, 3,5 , "UECL"))
new_teams.append(("Pot 1", 5, "Gent", "KAA Gent (BEL)", 37.500, 1,4 , "UECL"))
new_teams.append(("Pot 1", 6, "Fener", "Fenerbahçe SK (TUR)", 30.000, 3,5 , "UECL"))
new_teams.append(("Pot 2", 7, "Monac", "AS Monaco FC (FRA)", 29.000, 4,5 , "UECL"))
new_teams.append(("Pot 2", 8, "Cluj", "CFR 1907 Cluj (ROU)", 27.500, 1,5 , "UECL"))
new_teams.append(("Pot 2", 9, "Midty", "FC Midtjylland (DEN)", 25.500, 1,5 , "UECL"))
new_teams.append(("Pot 2", 10, "PAOK", "PAOK FC (GRE)", 25.000, 1,3 , "UECL"))
new_teams.append(("Pot 2", 11, "Brati", "ŠK Slovan Bratislava (SVK)", 24.500, 1,5 , "UECL"))
new_teams.append(("Pot 2", 12, "Macca", "Maccabi Tel-Aviv FC (ISR)", 24.000, 1,5 , "UECL"))
new_teams.append(("Pot 3", 13, "Plzeň", "FC Viktoria Plzeň (CZE)", 22.000, 2,4 , "UECL"))
new_teams.append(("Pot 3", 14, "Ludog", "PFC Ludogorets 1945 (BUL)", 21.000, 1,5 , "UECL"))
new_teams.append(("Pot 3", 15, "Glimt", "FK Bodø/Glimt (NOR)", 20.000, 2,5 , "UECL"))
new_teams.append(("Pot 3", 16, "Osaun", "CA Osasuna (ESP)", 18.599, 3,3 , "UECL"))
new_teams.append(("Pot 3", 17, "Genk", "KRC Genk (BEL)", 18.000, 1,4 , "UECL"))
new_teams.append(("Pot 3", 18, "Bolog", "FC Bologna (ITA)", 16.385, 3,3 , "UECL"))
new_teams.append(("Pot 4", 19, "Luhan", "FC Zorya Luhansk (UKR)", 16.000, 1,3 , "UECL"))
new_teams.append(("Pot 4", 20, "Astana", "FC Astana (KAZ)", 14.000, 1,5 , "UECL"))
new_teams.append(("Pot 4", 21, "Beşikt", "Beşiktaş (TUR)", 14.000, 3,5 , "UECL"))
new_teams.append(("Pot 4", 22, "Vilni", "FK Žalgiris Vilnius (LTU)", 11.000, 1,5 , "UECL"))
new_teams.append(("Pot 4", 23, "Helsi", "HJK Helsinki (FIN)", 11.000, 1,5 , "UECL"))
new_teams.append(("Pot 4", 24, "Flora", "FC Flora Tallinn (EST)", 10.500, 1,5 , "UECL"))
new_teams.append(("Pot 5", 25, "Legia", "Legia Warszawa (POL)", 11.000, 1,5 , "UECL"))
new_teams.append(("Pot 5", 26, "Trna", "FC Spartak Trnava (SVK)", 10.500, 1,4 , "UECL"))
new_teams.append(("Pot 5", 27, "Ljubl", "NK Olimpija Ljubljana (SVN)", 9.000, 1,5 , "UECL"))
new_teams.append(("Pot 5", 28, "Zrinj", "HŠK Zrinjski (BIH)", 8.500, 1,5 , "UECL"))
new_teams.append(("Pot 5", 29, "Dnipr", "Dnipro-1 (UKR)", 8.000, 1,3 , "UECL"))
new_teams.append(("Pot 5", 30, "Klaks", "KÍ Klaksvík (FRO)", 8.000, 1,5 , "UECL"))
new_teams.append(("Pot 6", 31, "Aberd", "Aberdeen FC (SCO)", 8.000, 2,3 , "UECL"))
new_teams.append(("Pot 6", 32, "Čukar", "FK Čukarički (SRB)", 6.475, 1,5 , "UECL"))
new_teams.append(("Pot 6", 33, "Lugano", "FC Lugano (SUI)", 6.335, 1,3 , "UECL"))
new_teams.append(("Pot 6", 34, "Breida", "Breidablik (ISL)", 6.000, 1,5 , "UECL"))
new_teams.append(("Pot 6", 35, "Nordsj", "FC Nordsjælland (DEN)", 5.565, 1,5 , "UECL"))
new_teams.append(("Pot 6", 36, "Ballk", "Ballkani (KOS)", 3.000, 1,5 , "UECL"))
CET_minus_1 = ['ENG','POR','SCO']
CET_plus_1 = ['TUR','AZE','ISR','UKR']
# %%
for i in range(1,6):
Conference.objects.get_or_create(scenario=scenario,name=f"Global Coeff {i}")
Conference.objects.get_or_create(scenario=scenario,name=f"Domestic Coeff {i}")
Conference.objects.get_or_create(scenario=scenario,name="CET")
Conference.objects.get_or_create(scenario=scenario,name="CET-1")
Conference.objects.get_or_create(scenario=scenario,name="CET+1")
for conf in Conference.objects.filter(scenario=scenario):
conf.teams.clear()
conf.collapseInView = True
conf.save()
Team.objects.filter(season=scenario.season).update(active=False)
for t in new_teams:
team_name = t[3].split('(')[0].strip()
team_country = t[3].split('(')[1].split(')')[0].strip()
abbreviation = t[2]
global_coeff = t[5]
domestic_coeff = t[6]
pot = int(t[0].split(' ')[1].strip())
pos = int(t[1])
competition = t[7]
teamObj = Team.objects.filter(season=scenario.season,name=team_name)
if teamObj:
pass
else:
print(t,"->", team_name)
gteam = GlobalTeam.objects.filter(name=team_name)
if gteam:
teamObj = Team.objects.create(season=scenario.season,
name=team_name,
attractivity=global_coeff+0.1*domestic_coeff,
position=pos,
pot=pot,
latitude=gteam.first().latitude,
longitude=gteam.first().longitude,
country=gteam.first().country,
active=True)
print("\tCreated team from global", team_name)
teamObj = Team.objects.filter(season=scenario.season,name=team_name)
else:
print("\tTeam not found", team_name)
continue
Conference.objects.filter(scenario=scenario,name=competition).first().teams.add(teamObj.first())
Conference.objects.filter(scenario=scenario,name=f"{competition}-{t[0]}").first().teams.add(teamObj.first())
if global_coeff in range(1,6):
Conference.objects.filter(scenario=scenario,name=f"Global Coeff {global_coeff}").first().teams.add(teamObj.first())
if domestic_coeff in range(1,6):
Conference.objects.filter(scenario=scenario,name=f"Domestic Coeff {domestic_coeff}").first().teams.add(teamObj.first())
if team_country in CET_minus_1:
Conference.objects.filter(scenario=scenario,name="CET-1").first().teams.add(teamObj.first())
elif team_country in CET_plus_1:
Conference.objects.filter(scenario=scenario,name="CET+1").first().teams.add(teamObj.first())
else:
Conference.objects.filter(scenario=scenario,name="CET").first().teams.add(teamObj.first())
teamObj.update(active=True)
teamObj.update(attractivity=global_coeff+0.1*domestic_coeff)
if competition == "UEL":
teamObj.update(coefficient=5-pot)
if competition == "UECL":
teamObj.update(coefficient=7-pot)
teamObj.update(position=pos)
teamObj.update(pot=pot)
if teamObj.first().shortname == "":
teamObj.update(shortname=abbreviation)
for conf in Conference.objects.filter(scenario=scenario):
for t in conf.teams.filter(active=False):
conf.teams.remove(t)
for haw in HAWish.objects.filter(scenario=scenario):
for t in haw.teams.filter(active=False):
haw.teams.remove(t)
for enc in EncWish.objects.filter(scenario=scenario):
for t in enc.teams1.filter(active=False):
enc.teams1.remove(t)
for t in enc.teams2.filter(active=False):
enc.teams1.remove(t)
for pair in Pairing.objects.filter(scenario=scenario):
if pair.team1.active==False or pair.team2.active==False:
pair.delete()
# %%