Skip to main content

A python implementation of the whole-history-rating algorythm by Rémi Coulom (based on the ruby implementation at

Project description


a python convertion from the ruby implementation of Rémi Coulom's Whole-History Rating (WHR) algorithm.

the original code can be found here


pip install whole_history_rating


from whr import whole_history_rating

whr = whole_history_rating.Base()

# Base.create_game() arguments: black player name, white player name, winner, day number, handicap
# Handicap should generally be less than 500 elo
whr.create_game("shusaku", "shusai", "B", 1, 0)
whr.create_game("shusaku", "shusai", "W", 2, 0)
whr.create_game("shusaku", "shusai", "W", 3, 0)

# Iterate the WHR algorithm towards convergence with more players/games, more iterations are needed.

# Or let the module iterate until the elo is stable (precision by default 10E-3) with a time limit of 10 seconds by default
whr.auto_iterate(time_limit = 10, precision = 10E-3)

# Results are stored in one triplet for each game: [day_number, elo_rating, uncertainty]
whr.ratings_for_player("shusaku") => 
  [[1, -43, 84], 
   [2, -45, 84], 
   [3, -45, 84]]
whr.ratings_for_player("shusai") => 
  [[1, 43, 84], 
   [2, 45, 84], 
   [3, 45, 84]]

# You can print or get all ratings ordered
whr.print_ordered_ratings(current=False) # current to True to only get the last rank estimation
whr.get_ordered_ratings(current=False, compact=False) # compact to True to not have the name before each ranks

# You can get a prediction for a future game between two players (even non existing players)
# Base.probability_future_match() arguments: black player name, white player name, handicap
whr.probability_future_match("shusaku", "shusai",0) =>
  win probability: shusaku:37.24%; shusai:62.76%

# You can load several games all together using a file or a list of string representing the game
# all elements in list must be like: "black_name white_name winner time_step handicap extras" 
# you can exclude handicap (default=0) and extras (default={})
whr.load_games(["shusaku shusai B 1 0", "shusaku shusai W 2", "shusaku shusai W 3 0"])
whr.load_games(["firstname1 name1, firstname2 name2, W, 1"], separator=",")

# You can save and load a base (you don't have to redo all iterations)
whr2 = whole_history_rating.Base.load_base(path)

Optional Configuration

One of the meta parameters to WHR is the variance of rating change over one time step, :w2, which determines how much that a player's rating is likely change in one day. Higher numbers allow for faster progress. The default value is 300, which is fairly high.
Rémi Coulom in his paper, used w2=14 to get his results

whr = whole_history_rating.Base({'w2':14})

You can also set the base not case sensitive. "shusaku" and "ShUsAkU" will be the same.

whr = whole_history_rating.Base({'uncased':True})

Project details

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Files for whole-history-rating, version 1.5
Filename, size File type Python version Upload date Hashes
Filename, size whole_history_rating-1.5-py3-none-any.whl (10.8 kB) File type Wheel Python version py3 Upload date Hashes View
Filename, size whole_history_rating-1.5.tar.gz (10.8 kB) File type Source Python version None Upload date Hashes View

Supported by

AWS AWS Cloud computing Datadog Datadog Monitoring DigiCert DigiCert EV certificate Facebook / Instagram Facebook / Instagram PSF Sponsor Fastly Fastly CDN Google Google Object Storage and Download Analytics Microsoft Microsoft PSF Sponsor Pingdom Pingdom Monitoring Salesforce Salesforce PSF Sponsor Sentry Sentry Error logging StatusPage StatusPage Status page