TrueSkill is a rating system among game players. It was developed by
Microsoft Research and has been used on Xbox LIVE for ranking and
matchmaking service. This system quantifies players’ TRUE skill points by
the Bayesian inference algorithm. It also works well with any type of match
rule including N:N team game or free-for-all.

This project is a Python package which implements the TrueSkill rating
system:

fromtrueskillimportRating,quality_1vs1,rate_1vs1alice,bob=Rating(25),Rating(30)# assign Alice and Bob's ratingsifquality_1vs1(alice,bob)<0.50:print('This match seems to be not so fair')alice,bob=rate_1vs1(alice,bob)# update the ratings after the match

In TrueSkill, rating is a Gaussian distribution which starts from
\(\mathcal{ N }( 25, \frac{ 25 }{ 3 }^2 )\). \(\mu\) is an average
skill of player, and \(\sigma\) is a confidence of the guessed rating. A
real skill of player is between \(\mu \pm 2\sigma\) with 95% confidence.

>>> fromtrueskillimportRating>>> Rating()# use the default mu and sigmatrueskill.Rating(mu=25.000, sigma=8.333)

If some player’s rating is higher \(\beta\) than another player’s, the
player may have about a 76% (specifically \(\Phi(\frac {1}{\sqrt{2}})\))
chance to beat the other player. The default value of \(\beta\) is
\(\frac{ 25 }{ 6 }\).

Ratings will approach real skills through few times of the TrueSkill’s Bayesian
inference algorithm. How many matches TrueSkill needs to estimate real skills?
It depends on the game rule. See the below table:

There are many other match rules such as N:N team match, N:N:N multiple team
match, N:M unbalanced match, free-for-all (Player vs. All), and so on. Mostly
other rating systems cannot work with them but TrueSkill does. TrueSkill
accepts any types of matches.

Let’s assume that there are 2 teams which each has 2 players. The game was for
a hour but the one of players on the first team entered the game at 30 minutes
later.

If some player wasn’t present for the entire duration of the game, use the
concept of “partial play” by weights parameter. The above situation can be
described by the following weights:

1P on team A – 1.0 = Full time

2P on team A – 0.5 = \(\frac{ 30 }{ 60 }\) minutes

3P on team B – 1.0

4P on team B – 1.0

As a code with a 2-dimensional list:

# set each weights to 1, 0.5, 1, 1.rate([(r1,r2),(r3,r4)],weights=[(1,0.5),(1,1)])quality([(r1,r2),(r3,r4)],weights=[(1,0.5),(1,1)])

Or with a dictionary. Each keys are a tuple of
(team_index,index_or_key_of_rating):

# set a weight of 2nd player in 1st team to 0.5, otherwise leave as 1.rate([(r1,r2),(r3,r4)],weights={(0,1):0.5})# set a weight of Carol in 2nd team to 0.5, otherwise leave as 1.rate([{'alice':r1,'bob':r2},{'carol':r3}],weights={(1,'carol'):0.5})

Meanwhile, there are third-party libraries which implement the functions. You
may want to use another implementation because that’s more expert. Then set
backend option of TrueSkill to the backend you chose:

When winners have too lower rating than losers, TrueSkill.rate() will
raise FloatingPointError. In this case, you need higher
floating-point precision. The mpmath library offers flexible floating-point
precision. You can solve the problem with mpmath as a backend and higher
precision setting.

sigma – the initial standard deviation of ratings. The recommended
value is a third of mu.

beta – the distance which guarantees about 76% chance of winning.
The recommended value is a half of sigma.

tau – the dynamic factor which restrains a fixation of rating. The
recommended value is sigma per cent.

draw_probability – the draw probability between two teams. It can be
a float or function which returns a float
by the given two rating (team performance)
arguments and the beta value. If it is a
float, the game has fixed draw probability.
Otherwise, the draw probability will be decided
dynamically per each match.

backend – the name of a backend which implements cdf, pdf, ppf. See
trueskill.backends for more details. Defaults to
None.

rating_groups is a list of rating tuples or dictionaries that
represents each team of the match. You will get a result as same
structure as this argument. Rating dictionaries for this may be useful
to choose specific player’s new rating:

When winners have too lower rating than losers, TrueSkill.rate() will
raise FloatingPointError if the backend is None or “scipy”. But
from this version, you can avoid the problem with “mpmath” backend. This was
reported at issue #5.

This TrueSkill package is opened under the BSD license but the TrueSkill™
brand is not. Microsoft permits only Xbox Live games or non-commercial projects
to use TrueSkill™. If your project is commercial, you should find another
rating system. See LICENSE for the details.

I’m Heungsub Lee, a game developer. Any regarding questions or patches are
welcomed.