Advertisement
tzoonami

OWL ELO

Feb 24th, 2019
143
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 7.34 KB | None | 0 0
  1. import requests,random
  2. from operator import itemgetter
  3.  
  4. class Team:
  5.     def __init__(self, name, abbrev,maps):
  6.         self.name=name
  7.         self.abbrev=abbrev
  8.         self.elo=1000
  9.         self.maps = maps
  10.         self.assaultdraws = 0
  11.         self.assaultdrawable = 0
  12.         self.hybriddraws = 0
  13.         self.hybriddrawable = 0
  14.  
  15. def expected(A, B):
  16.     return 1 / (1 + 10 ** ((B - A) / 400))
  17. def elo(old, exp, score, k=24):
  18.     return old + k * (score - exp)
  19.  
  20. control = ["0x08000000000007E2","0x080000000000066D","0x08000000000004B7"]
  21. def tiebreakmap(mcmap):
  22.     tiebreaks = []
  23.     for cmap in control:
  24.         if mcmap != cmap:
  25.             tiebreaks.append(cmap)
  26.     return random.choice(tiebreaks)
  27. trials = 100000
  28. def simulate(A, B, gamemaps):
  29.     scorehist = {}
  30.     for i in range(trials):
  31.         score = (0,0)
  32.         for map in gamemaps:
  33.  
  34.             if map in assault:
  35.                 if random.random() < (((float(A.assaultdraws)/A.assaultdrawable)+(float(B.assaultdraws)/B.assaultdrawable))/2):
  36.                     continue
  37.             if map in hybrid:
  38.                 if random.random() < (((float(A.hybriddraws)/A.hybriddrawable)+(float(B.hybriddraws)/B.hybriddrawable)/2)):
  39.                     continue
  40.                
  41.            
  42.             if random.random() < expected(A.maps[map],B.maps[map]):
  43.                 score = (score[0]+1,score[1])
  44.             else:
  45.                 score = (score[0],score[1]+1)
  46.  
  47.         if score[0] == score[1]: # just in case of a (1,1) draw
  48.             tiebreak = tiebreakmap(gamemaps[0])
  49.             if random.random() < expected(A.maps[tiebreak],B.maps[tiebreak]):
  50.                 score = (score[0]+1,score[1])
  51.             else:
  52.                 score = (score[0],score[1]+1)
  53.  
  54.         if score in scorehist.keys():
  55.             scorehist[score] += 1
  56.         else:
  57.             scorehist[score] = 1
  58.  
  59.     return scorehist
  60.  
  61. def printhistogram(hist):
  62.     for score in hist.keys():
  63.         print("{0}-{1}: {2:.3f}".format(score[0],score[1],float(hist[score])/trials))
  64.            
  65.            
  66.            
  67.  
  68. if __name__ == "__main__":
  69.     teamresp = requests.get('https://api.overwatchleague.com/ranking')
  70.     if teamresp.status_code != 200:
  71.         raise ApiError('GET /ranking {}'.format(teamresp.status_code))
  72.     mapresp = requests.get('https://api.overwatchleague.com/maps')
  73.     if mapresp.status_code != 200:
  74.         raise ApiError('GET /ranking {}'.format(mapresp.status_code))
  75.     maps = {}
  76.     assault = []
  77.     hybrid = []
  78.     for map in mapresp.json():
  79.         maps[map['guid']]=map['name']['en_US']
  80.         if map['type'] == "hybrid":
  81.             hybrid.append(map['guid'])
  82.         if map['type'] == "assault":
  83.             assault.append(map['guid'])
  84.     #print(hybrid,assault)
  85.     #print(maps)
  86.     #print(teamresp.json()['content'][0])
  87.     teams = {}
  88.     for team in teamresp.json()['content']:
  89.         teammaps={}
  90.         for map in maps.keys():
  91.             teammaps[map] = 1000
  92.         teams[team['competitor']['id']] = Team(team['competitor']['name'],team['competitor']['abbreviatedName'],teammaps)
  93.     #for teamid in teams.keys():
  94.         #print(teamid,teams[teamid].name)
  95.     resp = requests.get('https://api.overwatchleague.com/schedule')
  96.     if resp.status_code != 200:
  97.         raise ApiError('GET /schedule {}'.format(resp.status_code))
  98.     #print(resp.json()['data']['stages'][0]['matches'][0]['games'][0]['attributes']['mapGuid'])
  99.     for match in resp.json()['data']['stages'][0]['matches']:
  100.         if match['state'] != "CONCLUDED":
  101.             break
  102.         A = teams[match['competitors'][0]['id']]
  103.         B = teams[match['competitors'][1]['id']]
  104.         #print(A.name, "vs", B.name)
  105.         for game in match['games']:
  106.             exp = expected(A.elo,B.elo)
  107.             gamemap = game['attributes']['mapGuid']
  108.             mapexp = expected(A.maps[gamemap],B.maps[gamemap])
  109.             #print("{0} vs {1} map {2} - {3} EV {4:.3f} map EV {5:.3f}".format(A.abbrev,B.abbrev,game['number'],maps[gamemap],exp,mapexp))
  110.  
  111.             assaultflag = False
  112.             hybridflag = False
  113.             if gamemap in assault:
  114.                 A.assaultdrawable += 1
  115.                 B.assaultdrawable += 1
  116.                 assaultflag = True
  117.             if gamemap in hybrid:
  118.                 A.hybriddrawable += 1
  119.                 B.hybriddrawable += 1
  120.                 hybridflag = True
  121.            
  122.             points = game['points']
  123.             if points[0] > points[1]:
  124.                 A.elo = elo(A.elo,exp,1)
  125.                 A.maps[gamemap] = elo(A.maps[gamemap],mapexp,1)
  126.                 B.elo = elo(B.elo,1-exp,0)
  127.                 B.maps[gamemap] = elo(B.maps[gamemap],1-mapexp,0)
  128.                 #print("{0} wins, ELOs {1:.1f} {2:.1f} {3:.1f} {4:.1f}".format(A.abbrev,A.elo,B.elo,A.maps[gamemap],B.maps[gamemap]))
  129.             elif points[0] < points[1]:
  130.                 A.elo = elo(A.elo,exp,0)
  131.                 A.maps[gamemap] = elo(A.maps[gamemap],mapexp,0)
  132.                 B.elo = elo(B.elo,1-exp,1)
  133.                 B.maps[gamemap] = elo(B.maps[gamemap],1-mapexp,1)
  134.                 #print("{0} wins, ELOs {1:.1f} {2:.1f} {3:.1f} {4:.1f}".format(B.abbrev,A.elo,B.elo,A.maps[gamemap],B.maps[gamemap]))
  135.             else:
  136.                 A.elo = elo(A.elo,exp,0.5)
  137.                 A.maps[gamemap] = elo(A.maps[gamemap],mapexp,0.5)
  138.                 B.elo = elo(B.elo,1-exp,0.5)
  139.                 B.maps[gamemap] = elo(B.maps[gamemap],1-mapexp,0.5)
  140.                 #print("draw, ELOs {0:.1f} {1:.1f} {2:.1f} {3:.1f}".format(A.elo,B.elo,A.maps[gamemap],B.maps[gamemap]))
  141.                 if assaultflag:
  142.                     A.assaultdraws += 1
  143.                     B.assaultdraws += 1
  144.                 if hybridflag:
  145.                     A.hybriddraws += 1
  146.                     B.hybriddraws += 1
  147.             #print()
  148.     i=1
  149.     predictions=4
  150.     for match in resp.json()['data']['stages'][0]['matches']:
  151.         if match['state'] == "CONCLUDED":
  152.             continue
  153.         A = teams[match['competitors'][0]['id']]
  154.         B = teams[match['competitors'][1]['id']]
  155.         print(A.name, "vs", B.name," - prediction EV ","{0:.3f}".format(expected(A.elo,B.elo)))
  156.         print()
  157.         gamemaps = []
  158.         for game in match['games']:
  159.             gamemap = game['attributes']['mapGuid']
  160.             gamemaps.append(gamemap)
  161.             mapexp = expected(A.maps[gamemap],B.maps[gamemap])
  162.             print("{0} vs {1} map {2} - {3} map EV {4:.3f}".format(A.abbrev,B.abbrev,game['number'],maps[gamemap],mapexp))
  163.             #if gamemap in hybrid:
  164.                 #print("Hybrid draw chance: {0} {1:.3f} {2} {3:.3f}".format(A.abbrev,float(A.hybriddraws)/A.hybriddrawable,B.abbrev,float(B.hybriddraws)/B.hybriddrawable))
  165.             #if gamemap in assault:
  166.                 #print("Assault draw chance: {0} {1:.3f} {2} {3:.3f}".format(A.abbrev,float(A.assaultdraws)/A.assaultdrawable,B.abbrev,float(B.assaultdraws)/B.assaultdrawable))
  167.             print()
  168.  
  169.         printhistogram(simulate(A,B,gamemaps))
  170.        
  171.         i+=1
  172.         if i>predictions:
  173.             break
  174.         print()
  175.         print()
  176.        
  177.        
  178.     teamelos = {}
  179.     for teamid in teams.keys():
  180.         teamelos[teamid]=teams[teamid].elo
  181.     i=1
  182.     for key, value in sorted(teamelos.items(), key = itemgetter(1), reverse = True):
  183.         print("{0}: {1} {2:.1f}".format(i,teams[key].name,value))
  184.         i+=1
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement