Fluorite | Level 6

## Program an Elo rating for sports teams

Hi,

I would like to program an "Elo" rating in SAS to rate sports teams. The Elo rating was originally developed to rate chess players. I would like this one to work as follows:

• Each team starts off with an initial rating of 1,000 points.
• For each match, each team contributes 5% of their current rating to the "Pot"
• The winning team collects the pot and that amount is added to the it's new (post match) rating
• The losing team does not take anything from the pot and their rating will decrease by how much they contributed
• If there is a tie, the pot will be split equally between to the two teams.

Example

• Lets say we have 3 teams, Team A, B and C
• First match is A v B. Each team's initial rating is 1,000 and they contribute 5% of that (50 points) each to the pot
• Team A wins and collects the pot. Their new rating is 1,050. Team B lose so take nothing, just lose the 50 points they contributed so their new rating is 950.
• Next match is B v C. B's pre match rating is 950 and they contribute 5% of that to the pot (48). It's team C's first match so their pre match rating is 1,000 and they contribute 5% (50) to the pot.
• Team B win and collect the pot so their new rating is 1,048. Team C lose so their rating decreases by the 50 they contributed. Their post match rating is 950.
• So at this point the team rating would read as follows:

Team A     1,050

Team B     1,048

Team C     950

See below the variables in my dataset (along with first few lines of sample data)

Date Team 1 Team 2          Winner

01jan2014     Team A Team B          Team A

05jan2014     Team B Team C          Team B

Thanks

cxkev182

1 ACCEPTED SOLUTION

Accepted Solutions
Super User

## Re: Program an Elo rating for sports teams

I don't understand.

1)

"The first match is A v B. Both of their pre match rating is 1,000 so they each contribute 5% of their rating to the pot (50 points each.)

Team A wins so their rating increases to 1,050. Team B loses so their rating decreases to 950."

TeamA would be 1,050( take 50 from TeamB). TeamB would be 950(lost 50).

2)

"The next match is B v C. B's current rating is 950 and they contribute 5% of that (48 points) to the point. This is C's first match so their rating is 1,000. They contribute 5% (50 points) to the pot."

TeamB would be 950+50(take 50 from TeamC) ??  TeamC would be 950(lost 50). ??

Why TeamB would be Team B  950+50+48= 1,048  ? That is right ?

Assuming the first scenario is right .

data have;

input Date : date9.     (  Team1     Team2     Winner ) (& \$);

format date date9.;

cards;

01jan2014     Team A     Team B     Team A

05jan2014     Team B     Team C     Team B

;

run;

data _null_;

if _n_ eq 1 then do;

length team \$ 80;

declare hash h();

h.definekey('team');

h.definedata('team','score');

h.definedone();

end;

set have end=last;

retain score 1000;

team=team1;h.replace();

team=team2;h.replace();

if last then h.output(dataset:'team');

run;

data _null_;

if _n_ eq 1 then do;

if 0 then set team;

declare hash h(dataset:'team');

h.definekey('team');

h.definedata('team','score');

h.definedone();

end;

set have end=last;

if winner=team1 then do;

h.find(key:team2);get=score*0.05;score=score-get; h.replace();

h.find(key:team1);score=score+get;h.replace();

end;

else if winner=team2 then do;

h.find(key:team1);get=score*0.05;score=score-get; h.replace();

h.find(key:team2);score=score+get;h.replace();

end;

if last then h.output(dataset:'want');

run;

Xia Keshan

3 REPLIES 3
Super User

## Re: Program an Elo rating for sports teams

I don't understand.

1)

"The first match is A v B. Both of their pre match rating is 1,000 so they each contribute 5% of their rating to the pot (50 points each.)

Team A wins so their rating increases to 1,050. Team B loses so their rating decreases to 950."

TeamA would be 1,050( take 50 from TeamB). TeamB would be 950(lost 50).

2)

"The next match is B v C. B's current rating is 950 and they contribute 5% of that (48 points) to the point. This is C's first match so their rating is 1,000. They contribute 5% (50 points) to the pot."

TeamB would be 950+50(take 50 from TeamC) ??  TeamC would be 950(lost 50). ??

Why TeamB would be Team B  950+50+48= 1,048  ? That is right ?

Assuming the first scenario is right .

data have;

input Date : date9.     (  Team1     Team2     Winner ) (& \$);

format date date9.;

cards;

01jan2014     Team A     Team B     Team A

05jan2014     Team B     Team C     Team B

;

run;

data _null_;

if _n_ eq 1 then do;

length team \$ 80;

declare hash h();

h.definekey('team');

h.definedata('team','score');

h.definedone();

end;

set have end=last;

retain score 1000;

team=team1;h.replace();

team=team2;h.replace();

if last then h.output(dataset:'team');

run;

data _null_;

if _n_ eq 1 then do;

if 0 then set team;

declare hash h(dataset:'team');

h.definekey('team');

h.definedata('team','score');

h.definedone();

end;

set have end=last;

if winner=team1 then do;

h.find(key:team2);get=score*0.05;score=score-get; h.replace();

h.find(key:team1);score=score+get;h.replace();

end;

else if winner=team2 then do;

h.find(key:team1);get=score*0.05;score=score-get; h.replace();

h.find(key:team2);score=score+get;h.replace();

end;

if last then h.output(dataset:'want');

run;

Xia Keshan

Quartz | Level 8

## Re: Program an Elo rating for sports teams

I developed other solution and I got the same result gotten by Xia-Keshan:

It can be easily generalized includying more teams in the Array and updating the do's.  I assume a null value of winner when the result is a draw:

data games;

infile cards truncover;

input date date9. team1 \$ team2 \$ winner \$ ;

format date date9.;

cards;

01jan2014 Team_A Team_B Team_A

05jan2014 Team_B Team_C Team_B

06jan2014 Team_C Team_A

;

run;

data winn_loss(drop=team:);

set games;

if winner = ' ' then do;

winner=team1;

losser=team1;

end;

else if winner = team1 then do;

losser=team2;

end;

else do;

winner=team2;

losser=team1;

end;

run;

data want(drop=i: pot:);

set winn_loss;

array team[3] Team_A Team_B Team_C (3*1000);

i_winn=0;

i_loss=0;

do i=1 to 3 while (i_winn=0);

if vinarrayx(winner) and vname(team)=winner then i_winn=i;

end;

do i=1 to 3 while (i_loss=0);

if vinarrayx(losser) and vname(team)=losser then i_loss=i;

end;

pot_win=round(team[i_winn]*0.05);

pot_los=round(team[i_loss]*0.05);

team[i_winn]=team[i_winn]+pot_los;

team[i_loss]=team[i_loss]-pot_los;

run;

CTorres

Fluorite | Level 6

## Re: Program an Elo rating for sports teams

That's great thanks for your help and apologies for my typo in the original question. I wish I could mark both as correct answer.

Discussion stats
• 3 replies
• 1372 views
• 3 likes
• 3 in conversation