Team matchmaking algorithm based on ELO









up vote
0
down vote

favorite












I'm looking for a very simple way to put up 2 teams out of unspecified(but known) amount of players. So its not actually a standard matchmaking since it only creates one match out of the whole pool of registered players for the specific match. I do have pretty much only single variable and it is the ELO score for each player, which means it's the only available option to base calculations on.



What I thought of is just simply go through every possible combination of a players(6 in each team) and the lowest difference between the average ELO of teams is the final rosters that get created. I've tested this option and it gives me more than 17mil calculations for 18 registered players(the amount of players shouldnt be more than 24 usually) so its doable but its definitely the MOST unoptimized way to do that.



So I decided to ask a question in here, maybe you can help me with that in some way. Any ideas what simple algos I can use or the ways of optimizing something in a straight up comparisons of all possible combinations.



If you want to provide any code examples I can read any code language(almost), so it doesnt really matter.



UPD. basically the input is gonna be a list of player objects that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects. The average ELO of both teams should be as close as possible.










share|improve this question























  • I'd probably start by organizing the players in a list ranking them by ELO and going from there instead of randomly assigning them or checking every combo you could just alternate who goes on which team... this probably won't yield perfect results in every case but will get you halfway there and then you can make balances to that, opposed to checking 17 million combinations for every match.
    – Ryan
    Nov 2 at 13:32






  • 2




    I just read your question a second time, and I still don't really know what the result is supposed to look like. I think I understand the input, but it's buried in a wall of text. Perhaps clarifying your requirements will also help clarify your thoughts on solutions.
    – Useless
    Nov 2 at 13:45










  • @Useless basically the input is gonna be a list of player objects, that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects
    – WardS
    Nov 2 at 14:17










  • Why did you tag it c++ and python if it's language agnostic...?
    – Matt Messersmith
    Nov 2 at 14:20










  • How many players per team? 6, right? And, most importantly, what are your criteria for choosing players? Do you want 2 teams with the same total ELO? Or the most similar? Or the minimum variance within the team? What?
    – Useless
    Nov 2 at 14:24














up vote
0
down vote

favorite












I'm looking for a very simple way to put up 2 teams out of unspecified(but known) amount of players. So its not actually a standard matchmaking since it only creates one match out of the whole pool of registered players for the specific match. I do have pretty much only single variable and it is the ELO score for each player, which means it's the only available option to base calculations on.



What I thought of is just simply go through every possible combination of a players(6 in each team) and the lowest difference between the average ELO of teams is the final rosters that get created. I've tested this option and it gives me more than 17mil calculations for 18 registered players(the amount of players shouldnt be more than 24 usually) so its doable but its definitely the MOST unoptimized way to do that.



So I decided to ask a question in here, maybe you can help me with that in some way. Any ideas what simple algos I can use or the ways of optimizing something in a straight up comparisons of all possible combinations.



If you want to provide any code examples I can read any code language(almost), so it doesnt really matter.



UPD. basically the input is gonna be a list of player objects that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects. The average ELO of both teams should be as close as possible.










share|improve this question























  • I'd probably start by organizing the players in a list ranking them by ELO and going from there instead of randomly assigning them or checking every combo you could just alternate who goes on which team... this probably won't yield perfect results in every case but will get you halfway there and then you can make balances to that, opposed to checking 17 million combinations for every match.
    – Ryan
    Nov 2 at 13:32






  • 2




    I just read your question a second time, and I still don't really know what the result is supposed to look like. I think I understand the input, but it's buried in a wall of text. Perhaps clarifying your requirements will also help clarify your thoughts on solutions.
    – Useless
    Nov 2 at 13:45










  • @Useless basically the input is gonna be a list of player objects, that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects
    – WardS
    Nov 2 at 14:17










  • Why did you tag it c++ and python if it's language agnostic...?
    – Matt Messersmith
    Nov 2 at 14:20










  • How many players per team? 6, right? And, most importantly, what are your criteria for choosing players? Do you want 2 teams with the same total ELO? Or the most similar? Or the minimum variance within the team? What?
    – Useless
    Nov 2 at 14:24












up vote
0
down vote

favorite









up vote
0
down vote

favorite











I'm looking for a very simple way to put up 2 teams out of unspecified(but known) amount of players. So its not actually a standard matchmaking since it only creates one match out of the whole pool of registered players for the specific match. I do have pretty much only single variable and it is the ELO score for each player, which means it's the only available option to base calculations on.



What I thought of is just simply go through every possible combination of a players(6 in each team) and the lowest difference between the average ELO of teams is the final rosters that get created. I've tested this option and it gives me more than 17mil calculations for 18 registered players(the amount of players shouldnt be more than 24 usually) so its doable but its definitely the MOST unoptimized way to do that.



So I decided to ask a question in here, maybe you can help me with that in some way. Any ideas what simple algos I can use or the ways of optimizing something in a straight up comparisons of all possible combinations.



If you want to provide any code examples I can read any code language(almost), so it doesnt really matter.



UPD. basically the input is gonna be a list of player objects that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects. The average ELO of both teams should be as close as possible.










share|improve this question















I'm looking for a very simple way to put up 2 teams out of unspecified(but known) amount of players. So its not actually a standard matchmaking since it only creates one match out of the whole pool of registered players for the specific match. I do have pretty much only single variable and it is the ELO score for each player, which means it's the only available option to base calculations on.



What I thought of is just simply go through every possible combination of a players(6 in each team) and the lowest difference between the average ELO of teams is the final rosters that get created. I've tested this option and it gives me more than 17mil calculations for 18 registered players(the amount of players shouldnt be more than 24 usually) so its doable but its definitely the MOST unoptimized way to do that.



So I decided to ask a question in here, maybe you can help me with that in some way. Any ideas what simple algos I can use or the ways of optimizing something in a straight up comparisons of all possible combinations.



If you want to provide any code examples I can read any code language(almost), so it doesnt really matter.



UPD. basically the input is gonna be a list of player objects that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects. The average ELO of both teams should be as close as possible.







python c++ algorithm math combinations






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Nov 2 at 15:23

























asked Nov 2 at 13:22









WardS

8310




8310











  • I'd probably start by organizing the players in a list ranking them by ELO and going from there instead of randomly assigning them or checking every combo you could just alternate who goes on which team... this probably won't yield perfect results in every case but will get you halfway there and then you can make balances to that, opposed to checking 17 million combinations for every match.
    – Ryan
    Nov 2 at 13:32






  • 2




    I just read your question a second time, and I still don't really know what the result is supposed to look like. I think I understand the input, but it's buried in a wall of text. Perhaps clarifying your requirements will also help clarify your thoughts on solutions.
    – Useless
    Nov 2 at 13:45










  • @Useless basically the input is gonna be a list of player objects, that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects
    – WardS
    Nov 2 at 14:17










  • Why did you tag it c++ and python if it's language agnostic...?
    – Matt Messersmith
    Nov 2 at 14:20










  • How many players per team? 6, right? And, most importantly, what are your criteria for choosing players? Do you want 2 teams with the same total ELO? Or the most similar? Or the minimum variance within the team? What?
    – Useless
    Nov 2 at 14:24
















  • I'd probably start by organizing the players in a list ranking them by ELO and going from there instead of randomly assigning them or checking every combo you could just alternate who goes on which team... this probably won't yield perfect results in every case but will get you halfway there and then you can make balances to that, opposed to checking 17 million combinations for every match.
    – Ryan
    Nov 2 at 13:32






  • 2




    I just read your question a second time, and I still don't really know what the result is supposed to look like. I think I understand the input, but it's buried in a wall of text. Perhaps clarifying your requirements will also help clarify your thoughts on solutions.
    – Useless
    Nov 2 at 13:45










  • @Useless basically the input is gonna be a list of player objects, that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects
    – WardS
    Nov 2 at 14:17










  • Why did you tag it c++ and python if it's language agnostic...?
    – Matt Messersmith
    Nov 2 at 14:20










  • How many players per team? 6, right? And, most importantly, what are your criteria for choosing players? Do you want 2 teams with the same total ELO? Or the most similar? Or the minimum variance within the team? What?
    – Useless
    Nov 2 at 14:24















I'd probably start by organizing the players in a list ranking them by ELO and going from there instead of randomly assigning them or checking every combo you could just alternate who goes on which team... this probably won't yield perfect results in every case but will get you halfway there and then you can make balances to that, opposed to checking 17 million combinations for every match.
– Ryan
Nov 2 at 13:32




I'd probably start by organizing the players in a list ranking them by ELO and going from there instead of randomly assigning them or checking every combo you could just alternate who goes on which team... this probably won't yield perfect results in every case but will get you halfway there and then you can make balances to that, opposed to checking 17 million combinations for every match.
– Ryan
Nov 2 at 13:32




2




2




I just read your question a second time, and I still don't really know what the result is supposed to look like. I think I understand the input, but it's buried in a wall of text. Perhaps clarifying your requirements will also help clarify your thoughts on solutions.
– Useless
Nov 2 at 13:45




I just read your question a second time, and I still don't really know what the result is supposed to look like. I think I understand the input, but it's buried in a wall of text. Perhaps clarifying your requirements will also help clarify your thoughts on solutions.
– Useless
Nov 2 at 13:45












@Useless basically the input is gonna be a list of player objects, that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects
– WardS
Nov 2 at 14:17




@Useless basically the input is gonna be a list of player objects, that contain player "id" and "elo", the output should be 2 team lists team1 and team2 containing player objects
– WardS
Nov 2 at 14:17












Why did you tag it c++ and python if it's language agnostic...?
– Matt Messersmith
Nov 2 at 14:20




Why did you tag it c++ and python if it's language agnostic...?
– Matt Messersmith
Nov 2 at 14:20












How many players per team? 6, right? And, most importantly, what are your criteria for choosing players? Do you want 2 teams with the same total ELO? Or the most similar? Or the minimum variance within the team? What?
– Useless
Nov 2 at 14:24




How many players per team? 6, right? And, most importantly, what are your criteria for choosing players? Do you want 2 teams with the same total ELO? Or the most similar? Or the minimum variance within the team? What?
– Useless
Nov 2 at 14:24












3 Answers
3






active

oldest

votes

















up vote
1
down vote



accepted










Given that your approach is an approximation anyways, putting too much effort to produce a perfect answer is a losing cause. Instead pick a reasonable difference and go from there.



I would suggest that you sort the list of players by ELO, then pair them up. Those people will be on opposing teams if they are included. If there are an odd number of people, leave out the person who is farthest from any other. Sort the pairs by difference and pair them up as well in the same way. That gives you fairly evenly matched groups of 4, and the teams will be the best and worst against the middle 2. These groups of 4 should generally be relatively close to even. Score it as the better group minus the worse one. (Either half can wind up better depending on actual scores.)



Now search for 3 groups of 4 such that A is as close as possible to the sum of B and C. The better group from A will go with the worse groups from B and C.



With 24 people this will be a virtually instantaneous calculation, and will give reasonable results.



The repeated difference approach that I started with is a well-known heuristic for the subset sum problem.




Given how fast this heuristic is, I think that it is worth broadening the search for a good team as follows.



  1. Sort your players. Put each player into a pair with the person above and below. With n players this will be n-1 pairs. Give each pair a score of either the ELO difference, or of how much more likely the better is to beat the worse. (Which I would choose depends on the way that the two play.)

  2. Sort your pairs. Pair each pair with the closest pair above and below who does not intersect it. With n-1 pairs this will usually result in n-2 groups of 4.

  3. Create a sorted list of groups of 4. Call it list4. Note that this list has size n + O(1).

  4. Construct a list of all groups of 8 that can be made from 2 groups of 4 that do not intersect. Sort it. Call it list8. The formula for how big this list is is complicated, but is n^2/2 + O(n) and took time O(n^2 log(n)) to sort.

  5. For each element of list4 find the nearest elements in list8 that are above/below it and have no players in common with it. For O(n) elements this is O(log(n)) expected work.

The result is that you get rid of the even/odd logic. Yes, you added back in some extra effort, but the biggest effort was the O(n^2 log(n)) to sort list8. This is sufficiently fast that you'll still produce very quick answers even if you had a hundred people thrown at it.



The result will be two evenly matched teams such that when they pair off by strength, the weaker team at least has a reasonable chance of posting a convincing upset.






share|improve this answer






















  • One possible improvement for your desired goal. After the first pairing, rather than scoring pairs with the rating difference, score them with the difference in odds of one beating the other. You can pull that calculation from wismuth.com/elo/calculator.html. And then proceed from there as above. This will give you 2 teams chosen so that the odds of one beating the other are very close.
    – btilly
    Nov 2 at 16:20










  • Thanks for your answer! I think that's the easiest solution and it's for sure what I was looking for. I'll test it out right now.
    – WardS
    Nov 2 at 17:16










  • @WardS I just added an explanation of how to broaden the search to produce better answers, though with still reasonable amounts of work.
    – btilly
    Nov 2 at 18:16

















up vote
5
down vote













We can write this as a mathematical optimization problem:



Say we have players i=1..24, and teams j=1,2. Introduce decision variables:



 x(i,j) = 1 if player i is assigned to team j
0 otherwise


Then we can write:



 Min |avg(2)-avg(1)|
subject to
sum(j, x(i,j)) <= 1 for all i (a player can be assigned only once)
sum(i, x(i,j)) = 6 for all j (a team needs 6 players)
avg(j) = sum(i, rating(i)*x(i,j)) / 6 (calculate the average)
avg(j) >= 0


We can linearize the absolute value in the objective:



 Min z
subject to
sum(j, x(i,j)) <= 1 for all i
sum(i, x(i,j)) = 6 for all j
avg(j) = sum(i, rating(i)*x(i,j)) / 6
-z <= avg(2)-avg(1) <= z
z >= 0, avg(j) >= 0


This is now a linear Mixed Integer Programming problem. MIP solvers are readily available.



Using some random data I get:



---- 43 PARAMETER r ELO rating

player1 1275, player2 1531, player3 1585, player4 668, player5 1107, player6 1011
player7 1242, player8 1774, player9 1096, player10 1400, player11 1036, player12 1538
player13 1135, player14 1206, player15 2153, player16 1112, player17 880, player18 850
player19 1528, player20 1875, player21 939, player22 1684, player23 1807, player24 1110


---- 43 VARIABLE x.L assignment

team1 team2

player1 1.000
player2 1.000
player4 1.000
player5 1.000
player6 1.000
player7 1.000
player8 1.000
player9 1.000
player10 1.000
player11 1.000
player17 1.000
player18 1.000


---- 43 VARIABLE avg.L average rating of team

team1 1155.833, team2 1155.833


---- 43 PARAMETER report solution report

team1 team2

player1 1275.000
player2 1531.000
player4 668.000
player5 1107.000
player6 1011.000
player7 1242.000
player8 1774.000
player9 1096.000
player10 1400.000
player11 1036.000
player17 880.000
player18 850.000
sum 6935.000 6935.000
avg 1155.833 1155.833


Surprisingly, for this data set we can find a perfect match.






share|improve this answer





























    up vote
    1
    down vote













    Here is a solution in MiniZinc:



    % Selecting Chess Players

    include "globals.mzn";

    int: noOfTeams = 2;
    int: noOfPlayers = 24;
    int: playersPerTeam = 6;

    set of int: Players = 1..noOfPlayers;
    set of int: Teams = 1..noOfTeams;

    array[Players] of int: elo =
    [1275, 1531, 1585, 668, 1107, 1011,
    1242, 1774, 1096, 1400, 1036, 1538,
    1135, 1206, 2153, 1112, 880, 850,
    1528, 1875, 939, 1684, 1807, 1110];

    array[Players] of var 0..noOfTeams: team;
    array[Teams] of var int: eloSums;

    % same number of players per team
    constraint forall(t in Teams) (
    playersPerTeam == sum([team[p] == t | p in Players])
    );

    % sum up the ELO numbers per team
    constraint forall(t in Teams) (
    eloSums[t] == sum([if team[p] == t then elo[p] else 0 endif | p in Players])
    );

    % enforce sorted sums to break symmetries
    % and avoid minimum/maximum predicates
    constraint forall(t1 in Teams, t2 in Teams where t1 < t2) (
    eloSums[t1] <= eloSums[t2]
    );

    solve minimize eloSums[noOfTeams] - eloSums[1];

    output ["n "] ++ ["team" ++ show(t) ++ " " | t in Teams] ++
    ["n"] ++
    [ if fix(team[p]) != 0 then
    if t == 1 then
    "nplayer" ++ show_int(-2,p) ++ " "
    else
    ""
    endif ++
    if fix(team[p]) == t then
    show_int(8, elo[p])
    else
    " "
    endif
    else
    ""
    endif
    | p in Players, t in Teams ] ++
    ["nsum "] ++
    [show_int(8, eloSums[t]) | t in Teams ] ++
    ["navg "] ++
    [show_float(8,2,eloSums[t]/playersPerTeam) | t in Teams ];


    The main decision variable is the array team. It assigns every player to one of the teams (0 = no team). To find a close ELO average, I sum up the ELO sums and enforce that minimum and maximum of all team sums are close together.






    share|improve this answer






















      Your Answer






      StackExchange.ifUsing("editor", function ()
      StackExchange.using("externalEditor", function ()
      StackExchange.using("snippets", function ()
      StackExchange.snippets.init();
      );
      );
      , "code-snippets");

      StackExchange.ready(function()
      var channelOptions =
      tags: "".split(" "),
      id: "1"
      ;
      initTagRenderer("".split(" "), "".split(" "), channelOptions);

      StackExchange.using("externalEditor", function()
      // Have to fire editor after snippets, if snippets enabled
      if (StackExchange.settings.snippets.snippetsEnabled)
      StackExchange.using("snippets", function()
      createEditor();
      );

      else
      createEditor();

      );

      function createEditor()
      StackExchange.prepareEditor(
      heartbeatType: 'answer',
      convertImagesToLinks: true,
      noModals: true,
      showLowRepImageUploadWarning: true,
      reputationToPostImages: 10,
      bindNavPrevention: true,
      postfix: "",
      imageUploader:
      brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
      contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
      allowUrls: true
      ,
      onDemand: true,
      discardSelector: ".discard-answer"
      ,immediatelyShowMarkdownHelp:true
      );



      );













      draft saved

      draft discarded


















      StackExchange.ready(
      function ()
      StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53119389%2fteam-matchmaking-algorithm-based-on-elo%23new-answer', 'question_page');

      );

      Post as a guest















      Required, but never shown

























      3 Answers
      3






      active

      oldest

      votes








      3 Answers
      3






      active

      oldest

      votes









      active

      oldest

      votes






      active

      oldest

      votes








      up vote
      1
      down vote



      accepted










      Given that your approach is an approximation anyways, putting too much effort to produce a perfect answer is a losing cause. Instead pick a reasonable difference and go from there.



      I would suggest that you sort the list of players by ELO, then pair them up. Those people will be on opposing teams if they are included. If there are an odd number of people, leave out the person who is farthest from any other. Sort the pairs by difference and pair them up as well in the same way. That gives you fairly evenly matched groups of 4, and the teams will be the best and worst against the middle 2. These groups of 4 should generally be relatively close to even. Score it as the better group minus the worse one. (Either half can wind up better depending on actual scores.)



      Now search for 3 groups of 4 such that A is as close as possible to the sum of B and C. The better group from A will go with the worse groups from B and C.



      With 24 people this will be a virtually instantaneous calculation, and will give reasonable results.



      The repeated difference approach that I started with is a well-known heuristic for the subset sum problem.




      Given how fast this heuristic is, I think that it is worth broadening the search for a good team as follows.



      1. Sort your players. Put each player into a pair with the person above and below. With n players this will be n-1 pairs. Give each pair a score of either the ELO difference, or of how much more likely the better is to beat the worse. (Which I would choose depends on the way that the two play.)

      2. Sort your pairs. Pair each pair with the closest pair above and below who does not intersect it. With n-1 pairs this will usually result in n-2 groups of 4.

      3. Create a sorted list of groups of 4. Call it list4. Note that this list has size n + O(1).

      4. Construct a list of all groups of 8 that can be made from 2 groups of 4 that do not intersect. Sort it. Call it list8. The formula for how big this list is is complicated, but is n^2/2 + O(n) and took time O(n^2 log(n)) to sort.

      5. For each element of list4 find the nearest elements in list8 that are above/below it and have no players in common with it. For O(n) elements this is O(log(n)) expected work.

      The result is that you get rid of the even/odd logic. Yes, you added back in some extra effort, but the biggest effort was the O(n^2 log(n)) to sort list8. This is sufficiently fast that you'll still produce very quick answers even if you had a hundred people thrown at it.



      The result will be two evenly matched teams such that when they pair off by strength, the weaker team at least has a reasonable chance of posting a convincing upset.






      share|improve this answer






















      • One possible improvement for your desired goal. After the first pairing, rather than scoring pairs with the rating difference, score them with the difference in odds of one beating the other. You can pull that calculation from wismuth.com/elo/calculator.html. And then proceed from there as above. This will give you 2 teams chosen so that the odds of one beating the other are very close.
        – btilly
        Nov 2 at 16:20










      • Thanks for your answer! I think that's the easiest solution and it's for sure what I was looking for. I'll test it out right now.
        – WardS
        Nov 2 at 17:16










      • @WardS I just added an explanation of how to broaden the search to produce better answers, though with still reasonable amounts of work.
        – btilly
        Nov 2 at 18:16














      up vote
      1
      down vote



      accepted










      Given that your approach is an approximation anyways, putting too much effort to produce a perfect answer is a losing cause. Instead pick a reasonable difference and go from there.



      I would suggest that you sort the list of players by ELO, then pair them up. Those people will be on opposing teams if they are included. If there are an odd number of people, leave out the person who is farthest from any other. Sort the pairs by difference and pair them up as well in the same way. That gives you fairly evenly matched groups of 4, and the teams will be the best and worst against the middle 2. These groups of 4 should generally be relatively close to even. Score it as the better group minus the worse one. (Either half can wind up better depending on actual scores.)



      Now search for 3 groups of 4 such that A is as close as possible to the sum of B and C. The better group from A will go with the worse groups from B and C.



      With 24 people this will be a virtually instantaneous calculation, and will give reasonable results.



      The repeated difference approach that I started with is a well-known heuristic for the subset sum problem.




      Given how fast this heuristic is, I think that it is worth broadening the search for a good team as follows.



      1. Sort your players. Put each player into a pair with the person above and below. With n players this will be n-1 pairs. Give each pair a score of either the ELO difference, or of how much more likely the better is to beat the worse. (Which I would choose depends on the way that the two play.)

      2. Sort your pairs. Pair each pair with the closest pair above and below who does not intersect it. With n-1 pairs this will usually result in n-2 groups of 4.

      3. Create a sorted list of groups of 4. Call it list4. Note that this list has size n + O(1).

      4. Construct a list of all groups of 8 that can be made from 2 groups of 4 that do not intersect. Sort it. Call it list8. The formula for how big this list is is complicated, but is n^2/2 + O(n) and took time O(n^2 log(n)) to sort.

      5. For each element of list4 find the nearest elements in list8 that are above/below it and have no players in common with it. For O(n) elements this is O(log(n)) expected work.

      The result is that you get rid of the even/odd logic. Yes, you added back in some extra effort, but the biggest effort was the O(n^2 log(n)) to sort list8. This is sufficiently fast that you'll still produce very quick answers even if you had a hundred people thrown at it.



      The result will be two evenly matched teams such that when they pair off by strength, the weaker team at least has a reasonable chance of posting a convincing upset.






      share|improve this answer






















      • One possible improvement for your desired goal. After the first pairing, rather than scoring pairs with the rating difference, score them with the difference in odds of one beating the other. You can pull that calculation from wismuth.com/elo/calculator.html. And then proceed from there as above. This will give you 2 teams chosen so that the odds of one beating the other are very close.
        – btilly
        Nov 2 at 16:20










      • Thanks for your answer! I think that's the easiest solution and it's for sure what I was looking for. I'll test it out right now.
        – WardS
        Nov 2 at 17:16










      • @WardS I just added an explanation of how to broaden the search to produce better answers, though with still reasonable amounts of work.
        – btilly
        Nov 2 at 18:16












      up vote
      1
      down vote



      accepted







      up vote
      1
      down vote



      accepted






      Given that your approach is an approximation anyways, putting too much effort to produce a perfect answer is a losing cause. Instead pick a reasonable difference and go from there.



      I would suggest that you sort the list of players by ELO, then pair them up. Those people will be on opposing teams if they are included. If there are an odd number of people, leave out the person who is farthest from any other. Sort the pairs by difference and pair them up as well in the same way. That gives you fairly evenly matched groups of 4, and the teams will be the best and worst against the middle 2. These groups of 4 should generally be relatively close to even. Score it as the better group minus the worse one. (Either half can wind up better depending on actual scores.)



      Now search for 3 groups of 4 such that A is as close as possible to the sum of B and C. The better group from A will go with the worse groups from B and C.



      With 24 people this will be a virtually instantaneous calculation, and will give reasonable results.



      The repeated difference approach that I started with is a well-known heuristic for the subset sum problem.




      Given how fast this heuristic is, I think that it is worth broadening the search for a good team as follows.



      1. Sort your players. Put each player into a pair with the person above and below. With n players this will be n-1 pairs. Give each pair a score of either the ELO difference, or of how much more likely the better is to beat the worse. (Which I would choose depends on the way that the two play.)

      2. Sort your pairs. Pair each pair with the closest pair above and below who does not intersect it. With n-1 pairs this will usually result in n-2 groups of 4.

      3. Create a sorted list of groups of 4. Call it list4. Note that this list has size n + O(1).

      4. Construct a list of all groups of 8 that can be made from 2 groups of 4 that do not intersect. Sort it. Call it list8. The formula for how big this list is is complicated, but is n^2/2 + O(n) and took time O(n^2 log(n)) to sort.

      5. For each element of list4 find the nearest elements in list8 that are above/below it and have no players in common with it. For O(n) elements this is O(log(n)) expected work.

      The result is that you get rid of the even/odd logic. Yes, you added back in some extra effort, but the biggest effort was the O(n^2 log(n)) to sort list8. This is sufficiently fast that you'll still produce very quick answers even if you had a hundred people thrown at it.



      The result will be two evenly matched teams such that when they pair off by strength, the weaker team at least has a reasonable chance of posting a convincing upset.






      share|improve this answer














      Given that your approach is an approximation anyways, putting too much effort to produce a perfect answer is a losing cause. Instead pick a reasonable difference and go from there.



      I would suggest that you sort the list of players by ELO, then pair them up. Those people will be on opposing teams if they are included. If there are an odd number of people, leave out the person who is farthest from any other. Sort the pairs by difference and pair them up as well in the same way. That gives you fairly evenly matched groups of 4, and the teams will be the best and worst against the middle 2. These groups of 4 should generally be relatively close to even. Score it as the better group minus the worse one. (Either half can wind up better depending on actual scores.)



      Now search for 3 groups of 4 such that A is as close as possible to the sum of B and C. The better group from A will go with the worse groups from B and C.



      With 24 people this will be a virtually instantaneous calculation, and will give reasonable results.



      The repeated difference approach that I started with is a well-known heuristic for the subset sum problem.




      Given how fast this heuristic is, I think that it is worth broadening the search for a good team as follows.



      1. Sort your players. Put each player into a pair with the person above and below. With n players this will be n-1 pairs. Give each pair a score of either the ELO difference, or of how much more likely the better is to beat the worse. (Which I would choose depends on the way that the two play.)

      2. Sort your pairs. Pair each pair with the closest pair above and below who does not intersect it. With n-1 pairs this will usually result in n-2 groups of 4.

      3. Create a sorted list of groups of 4. Call it list4. Note that this list has size n + O(1).

      4. Construct a list of all groups of 8 that can be made from 2 groups of 4 that do not intersect. Sort it. Call it list8. The formula for how big this list is is complicated, but is n^2/2 + O(n) and took time O(n^2 log(n)) to sort.

      5. For each element of list4 find the nearest elements in list8 that are above/below it and have no players in common with it. For O(n) elements this is O(log(n)) expected work.

      The result is that you get rid of the even/odd logic. Yes, you added back in some extra effort, but the biggest effort was the O(n^2 log(n)) to sort list8. This is sufficiently fast that you'll still produce very quick answers even if you had a hundred people thrown at it.



      The result will be two evenly matched teams such that when they pair off by strength, the weaker team at least has a reasonable chance of posting a convincing upset.







      share|improve this answer














      share|improve this answer



      share|improve this answer








      edited Nov 2 at 18:15

























      answered Nov 2 at 16:10









      btilly

      26k23853




      26k23853











      • One possible improvement for your desired goal. After the first pairing, rather than scoring pairs with the rating difference, score them with the difference in odds of one beating the other. You can pull that calculation from wismuth.com/elo/calculator.html. And then proceed from there as above. This will give you 2 teams chosen so that the odds of one beating the other are very close.
        – btilly
        Nov 2 at 16:20










      • Thanks for your answer! I think that's the easiest solution and it's for sure what I was looking for. I'll test it out right now.
        – WardS
        Nov 2 at 17:16










      • @WardS I just added an explanation of how to broaden the search to produce better answers, though with still reasonable amounts of work.
        – btilly
        Nov 2 at 18:16
















      • One possible improvement for your desired goal. After the first pairing, rather than scoring pairs with the rating difference, score them with the difference in odds of one beating the other. You can pull that calculation from wismuth.com/elo/calculator.html. And then proceed from there as above. This will give you 2 teams chosen so that the odds of one beating the other are very close.
        – btilly
        Nov 2 at 16:20










      • Thanks for your answer! I think that's the easiest solution and it's for sure what I was looking for. I'll test it out right now.
        – WardS
        Nov 2 at 17:16










      • @WardS I just added an explanation of how to broaden the search to produce better answers, though with still reasonable amounts of work.
        – btilly
        Nov 2 at 18:16















      One possible improvement for your desired goal. After the first pairing, rather than scoring pairs with the rating difference, score them with the difference in odds of one beating the other. You can pull that calculation from wismuth.com/elo/calculator.html. And then proceed from there as above. This will give you 2 teams chosen so that the odds of one beating the other are very close.
      – btilly
      Nov 2 at 16:20




      One possible improvement for your desired goal. After the first pairing, rather than scoring pairs with the rating difference, score them with the difference in odds of one beating the other. You can pull that calculation from wismuth.com/elo/calculator.html. And then proceed from there as above. This will give you 2 teams chosen so that the odds of one beating the other are very close.
      – btilly
      Nov 2 at 16:20












      Thanks for your answer! I think that's the easiest solution and it's for sure what I was looking for. I'll test it out right now.
      – WardS
      Nov 2 at 17:16




      Thanks for your answer! I think that's the easiest solution and it's for sure what I was looking for. I'll test it out right now.
      – WardS
      Nov 2 at 17:16












      @WardS I just added an explanation of how to broaden the search to produce better answers, though with still reasonable amounts of work.
      – btilly
      Nov 2 at 18:16




      @WardS I just added an explanation of how to broaden the search to produce better answers, though with still reasonable amounts of work.
      – btilly
      Nov 2 at 18:16












      up vote
      5
      down vote













      We can write this as a mathematical optimization problem:



      Say we have players i=1..24, and teams j=1,2. Introduce decision variables:



       x(i,j) = 1 if player i is assigned to team j
      0 otherwise


      Then we can write:



       Min |avg(2)-avg(1)|
      subject to
      sum(j, x(i,j)) <= 1 for all i (a player can be assigned only once)
      sum(i, x(i,j)) = 6 for all j (a team needs 6 players)
      avg(j) = sum(i, rating(i)*x(i,j)) / 6 (calculate the average)
      avg(j) >= 0


      We can linearize the absolute value in the objective:



       Min z
      subject to
      sum(j, x(i,j)) <= 1 for all i
      sum(i, x(i,j)) = 6 for all j
      avg(j) = sum(i, rating(i)*x(i,j)) / 6
      -z <= avg(2)-avg(1) <= z
      z >= 0, avg(j) >= 0


      This is now a linear Mixed Integer Programming problem. MIP solvers are readily available.



      Using some random data I get:



      ---- 43 PARAMETER r ELO rating

      player1 1275, player2 1531, player3 1585, player4 668, player5 1107, player6 1011
      player7 1242, player8 1774, player9 1096, player10 1400, player11 1036, player12 1538
      player13 1135, player14 1206, player15 2153, player16 1112, player17 880, player18 850
      player19 1528, player20 1875, player21 939, player22 1684, player23 1807, player24 1110


      ---- 43 VARIABLE x.L assignment

      team1 team2

      player1 1.000
      player2 1.000
      player4 1.000
      player5 1.000
      player6 1.000
      player7 1.000
      player8 1.000
      player9 1.000
      player10 1.000
      player11 1.000
      player17 1.000
      player18 1.000


      ---- 43 VARIABLE avg.L average rating of team

      team1 1155.833, team2 1155.833


      ---- 43 PARAMETER report solution report

      team1 team2

      player1 1275.000
      player2 1531.000
      player4 668.000
      player5 1107.000
      player6 1011.000
      player7 1242.000
      player8 1774.000
      player9 1096.000
      player10 1400.000
      player11 1036.000
      player17 880.000
      player18 850.000
      sum 6935.000 6935.000
      avg 1155.833 1155.833


      Surprisingly, for this data set we can find a perfect match.






      share|improve this answer


























        up vote
        5
        down vote













        We can write this as a mathematical optimization problem:



        Say we have players i=1..24, and teams j=1,2. Introduce decision variables:



         x(i,j) = 1 if player i is assigned to team j
        0 otherwise


        Then we can write:



         Min |avg(2)-avg(1)|
        subject to
        sum(j, x(i,j)) <= 1 for all i (a player can be assigned only once)
        sum(i, x(i,j)) = 6 for all j (a team needs 6 players)
        avg(j) = sum(i, rating(i)*x(i,j)) / 6 (calculate the average)
        avg(j) >= 0


        We can linearize the absolute value in the objective:



         Min z
        subject to
        sum(j, x(i,j)) <= 1 for all i
        sum(i, x(i,j)) = 6 for all j
        avg(j) = sum(i, rating(i)*x(i,j)) / 6
        -z <= avg(2)-avg(1) <= z
        z >= 0, avg(j) >= 0


        This is now a linear Mixed Integer Programming problem. MIP solvers are readily available.



        Using some random data I get:



        ---- 43 PARAMETER r ELO rating

        player1 1275, player2 1531, player3 1585, player4 668, player5 1107, player6 1011
        player7 1242, player8 1774, player9 1096, player10 1400, player11 1036, player12 1538
        player13 1135, player14 1206, player15 2153, player16 1112, player17 880, player18 850
        player19 1528, player20 1875, player21 939, player22 1684, player23 1807, player24 1110


        ---- 43 VARIABLE x.L assignment

        team1 team2

        player1 1.000
        player2 1.000
        player4 1.000
        player5 1.000
        player6 1.000
        player7 1.000
        player8 1.000
        player9 1.000
        player10 1.000
        player11 1.000
        player17 1.000
        player18 1.000


        ---- 43 VARIABLE avg.L average rating of team

        team1 1155.833, team2 1155.833


        ---- 43 PARAMETER report solution report

        team1 team2

        player1 1275.000
        player2 1531.000
        player4 668.000
        player5 1107.000
        player6 1011.000
        player7 1242.000
        player8 1774.000
        player9 1096.000
        player10 1400.000
        player11 1036.000
        player17 880.000
        player18 850.000
        sum 6935.000 6935.000
        avg 1155.833 1155.833


        Surprisingly, for this data set we can find a perfect match.






        share|improve this answer
























          up vote
          5
          down vote










          up vote
          5
          down vote









          We can write this as a mathematical optimization problem:



          Say we have players i=1..24, and teams j=1,2. Introduce decision variables:



           x(i,j) = 1 if player i is assigned to team j
          0 otherwise


          Then we can write:



           Min |avg(2)-avg(1)|
          subject to
          sum(j, x(i,j)) <= 1 for all i (a player can be assigned only once)
          sum(i, x(i,j)) = 6 for all j (a team needs 6 players)
          avg(j) = sum(i, rating(i)*x(i,j)) / 6 (calculate the average)
          avg(j) >= 0


          We can linearize the absolute value in the objective:



           Min z
          subject to
          sum(j, x(i,j)) <= 1 for all i
          sum(i, x(i,j)) = 6 for all j
          avg(j) = sum(i, rating(i)*x(i,j)) / 6
          -z <= avg(2)-avg(1) <= z
          z >= 0, avg(j) >= 0


          This is now a linear Mixed Integer Programming problem. MIP solvers are readily available.



          Using some random data I get:



          ---- 43 PARAMETER r ELO rating

          player1 1275, player2 1531, player3 1585, player4 668, player5 1107, player6 1011
          player7 1242, player8 1774, player9 1096, player10 1400, player11 1036, player12 1538
          player13 1135, player14 1206, player15 2153, player16 1112, player17 880, player18 850
          player19 1528, player20 1875, player21 939, player22 1684, player23 1807, player24 1110


          ---- 43 VARIABLE x.L assignment

          team1 team2

          player1 1.000
          player2 1.000
          player4 1.000
          player5 1.000
          player6 1.000
          player7 1.000
          player8 1.000
          player9 1.000
          player10 1.000
          player11 1.000
          player17 1.000
          player18 1.000


          ---- 43 VARIABLE avg.L average rating of team

          team1 1155.833, team2 1155.833


          ---- 43 PARAMETER report solution report

          team1 team2

          player1 1275.000
          player2 1531.000
          player4 668.000
          player5 1107.000
          player6 1011.000
          player7 1242.000
          player8 1774.000
          player9 1096.000
          player10 1400.000
          player11 1036.000
          player17 880.000
          player18 850.000
          sum 6935.000 6935.000
          avg 1155.833 1155.833


          Surprisingly, for this data set we can find a perfect match.






          share|improve this answer














          We can write this as a mathematical optimization problem:



          Say we have players i=1..24, and teams j=1,2. Introduce decision variables:



           x(i,j) = 1 if player i is assigned to team j
          0 otherwise


          Then we can write:



           Min |avg(2)-avg(1)|
          subject to
          sum(j, x(i,j)) <= 1 for all i (a player can be assigned only once)
          sum(i, x(i,j)) = 6 for all j (a team needs 6 players)
          avg(j) = sum(i, rating(i)*x(i,j)) / 6 (calculate the average)
          avg(j) >= 0


          We can linearize the absolute value in the objective:



           Min z
          subject to
          sum(j, x(i,j)) <= 1 for all i
          sum(i, x(i,j)) = 6 for all j
          avg(j) = sum(i, rating(i)*x(i,j)) / 6
          -z <= avg(2)-avg(1) <= z
          z >= 0, avg(j) >= 0


          This is now a linear Mixed Integer Programming problem. MIP solvers are readily available.



          Using some random data I get:



          ---- 43 PARAMETER r ELO rating

          player1 1275, player2 1531, player3 1585, player4 668, player5 1107, player6 1011
          player7 1242, player8 1774, player9 1096, player10 1400, player11 1036, player12 1538
          player13 1135, player14 1206, player15 2153, player16 1112, player17 880, player18 850
          player19 1528, player20 1875, player21 939, player22 1684, player23 1807, player24 1110


          ---- 43 VARIABLE x.L assignment

          team1 team2

          player1 1.000
          player2 1.000
          player4 1.000
          player5 1.000
          player6 1.000
          player7 1.000
          player8 1.000
          player9 1.000
          player10 1.000
          player11 1.000
          player17 1.000
          player18 1.000


          ---- 43 VARIABLE avg.L average rating of team

          team1 1155.833, team2 1155.833


          ---- 43 PARAMETER report solution report

          team1 team2

          player1 1275.000
          player2 1531.000
          player4 668.000
          player5 1107.000
          player6 1011.000
          player7 1242.000
          player8 1774.000
          player9 1096.000
          player10 1400.000
          player11 1036.000
          player17 880.000
          player18 850.000
          sum 6935.000 6935.000
          avg 1155.833 1155.833


          Surprisingly, for this data set we can find a perfect match.







          share|improve this answer














          share|improve this answer



          share|improve this answer








          edited Nov 12 at 15:22

























          answered Nov 11 at 7:28









          Erwin Kalvelagen

          4,6962423




          4,6962423




















              up vote
              1
              down vote













              Here is a solution in MiniZinc:



              % Selecting Chess Players

              include "globals.mzn";

              int: noOfTeams = 2;
              int: noOfPlayers = 24;
              int: playersPerTeam = 6;

              set of int: Players = 1..noOfPlayers;
              set of int: Teams = 1..noOfTeams;

              array[Players] of int: elo =
              [1275, 1531, 1585, 668, 1107, 1011,
              1242, 1774, 1096, 1400, 1036, 1538,
              1135, 1206, 2153, 1112, 880, 850,
              1528, 1875, 939, 1684, 1807, 1110];

              array[Players] of var 0..noOfTeams: team;
              array[Teams] of var int: eloSums;

              % same number of players per team
              constraint forall(t in Teams) (
              playersPerTeam == sum([team[p] == t | p in Players])
              );

              % sum up the ELO numbers per team
              constraint forall(t in Teams) (
              eloSums[t] == sum([if team[p] == t then elo[p] else 0 endif | p in Players])
              );

              % enforce sorted sums to break symmetries
              % and avoid minimum/maximum predicates
              constraint forall(t1 in Teams, t2 in Teams where t1 < t2) (
              eloSums[t1] <= eloSums[t2]
              );

              solve minimize eloSums[noOfTeams] - eloSums[1];

              output ["n "] ++ ["team" ++ show(t) ++ " " | t in Teams] ++
              ["n"] ++
              [ if fix(team[p]) != 0 then
              if t == 1 then
              "nplayer" ++ show_int(-2,p) ++ " "
              else
              ""
              endif ++
              if fix(team[p]) == t then
              show_int(8, elo[p])
              else
              " "
              endif
              else
              ""
              endif
              | p in Players, t in Teams ] ++
              ["nsum "] ++
              [show_int(8, eloSums[t]) | t in Teams ] ++
              ["navg "] ++
              [show_float(8,2,eloSums[t]/playersPerTeam) | t in Teams ];


              The main decision variable is the array team. It assigns every player to one of the teams (0 = no team). To find a close ELO average, I sum up the ELO sums and enforce that minimum and maximum of all team sums are close together.






              share|improve this answer


























                up vote
                1
                down vote













                Here is a solution in MiniZinc:



                % Selecting Chess Players

                include "globals.mzn";

                int: noOfTeams = 2;
                int: noOfPlayers = 24;
                int: playersPerTeam = 6;

                set of int: Players = 1..noOfPlayers;
                set of int: Teams = 1..noOfTeams;

                array[Players] of int: elo =
                [1275, 1531, 1585, 668, 1107, 1011,
                1242, 1774, 1096, 1400, 1036, 1538,
                1135, 1206, 2153, 1112, 880, 850,
                1528, 1875, 939, 1684, 1807, 1110];

                array[Players] of var 0..noOfTeams: team;
                array[Teams] of var int: eloSums;

                % same number of players per team
                constraint forall(t in Teams) (
                playersPerTeam == sum([team[p] == t | p in Players])
                );

                % sum up the ELO numbers per team
                constraint forall(t in Teams) (
                eloSums[t] == sum([if team[p] == t then elo[p] else 0 endif | p in Players])
                );

                % enforce sorted sums to break symmetries
                % and avoid minimum/maximum predicates
                constraint forall(t1 in Teams, t2 in Teams where t1 < t2) (
                eloSums[t1] <= eloSums[t2]
                );

                solve minimize eloSums[noOfTeams] - eloSums[1];

                output ["n "] ++ ["team" ++ show(t) ++ " " | t in Teams] ++
                ["n"] ++
                [ if fix(team[p]) != 0 then
                if t == 1 then
                "nplayer" ++ show_int(-2,p) ++ " "
                else
                ""
                endif ++
                if fix(team[p]) == t then
                show_int(8, elo[p])
                else
                " "
                endif
                else
                ""
                endif
                | p in Players, t in Teams ] ++
                ["nsum "] ++
                [show_int(8, eloSums[t]) | t in Teams ] ++
                ["navg "] ++
                [show_float(8,2,eloSums[t]/playersPerTeam) | t in Teams ];


                The main decision variable is the array team. It assigns every player to one of the teams (0 = no team). To find a close ELO average, I sum up the ELO sums and enforce that minimum and maximum of all team sums are close together.






                share|improve this answer
























                  up vote
                  1
                  down vote










                  up vote
                  1
                  down vote









                  Here is a solution in MiniZinc:



                  % Selecting Chess Players

                  include "globals.mzn";

                  int: noOfTeams = 2;
                  int: noOfPlayers = 24;
                  int: playersPerTeam = 6;

                  set of int: Players = 1..noOfPlayers;
                  set of int: Teams = 1..noOfTeams;

                  array[Players] of int: elo =
                  [1275, 1531, 1585, 668, 1107, 1011,
                  1242, 1774, 1096, 1400, 1036, 1538,
                  1135, 1206, 2153, 1112, 880, 850,
                  1528, 1875, 939, 1684, 1807, 1110];

                  array[Players] of var 0..noOfTeams: team;
                  array[Teams] of var int: eloSums;

                  % same number of players per team
                  constraint forall(t in Teams) (
                  playersPerTeam == sum([team[p] == t | p in Players])
                  );

                  % sum up the ELO numbers per team
                  constraint forall(t in Teams) (
                  eloSums[t] == sum([if team[p] == t then elo[p] else 0 endif | p in Players])
                  );

                  % enforce sorted sums to break symmetries
                  % and avoid minimum/maximum predicates
                  constraint forall(t1 in Teams, t2 in Teams where t1 < t2) (
                  eloSums[t1] <= eloSums[t2]
                  );

                  solve minimize eloSums[noOfTeams] - eloSums[1];

                  output ["n "] ++ ["team" ++ show(t) ++ " " | t in Teams] ++
                  ["n"] ++
                  [ if fix(team[p]) != 0 then
                  if t == 1 then
                  "nplayer" ++ show_int(-2,p) ++ " "
                  else
                  ""
                  endif ++
                  if fix(team[p]) == t then
                  show_int(8, elo[p])
                  else
                  " "
                  endif
                  else
                  ""
                  endif
                  | p in Players, t in Teams ] ++
                  ["nsum "] ++
                  [show_int(8, eloSums[t]) | t in Teams ] ++
                  ["navg "] ++
                  [show_float(8,2,eloSums[t]/playersPerTeam) | t in Teams ];


                  The main decision variable is the array team. It assigns every player to one of the teams (0 = no team). To find a close ELO average, I sum up the ELO sums and enforce that minimum and maximum of all team sums are close together.






                  share|improve this answer














                  Here is a solution in MiniZinc:



                  % Selecting Chess Players

                  include "globals.mzn";

                  int: noOfTeams = 2;
                  int: noOfPlayers = 24;
                  int: playersPerTeam = 6;

                  set of int: Players = 1..noOfPlayers;
                  set of int: Teams = 1..noOfTeams;

                  array[Players] of int: elo =
                  [1275, 1531, 1585, 668, 1107, 1011,
                  1242, 1774, 1096, 1400, 1036, 1538,
                  1135, 1206, 2153, 1112, 880, 850,
                  1528, 1875, 939, 1684, 1807, 1110];

                  array[Players] of var 0..noOfTeams: team;
                  array[Teams] of var int: eloSums;

                  % same number of players per team
                  constraint forall(t in Teams) (
                  playersPerTeam == sum([team[p] == t | p in Players])
                  );

                  % sum up the ELO numbers per team
                  constraint forall(t in Teams) (
                  eloSums[t] == sum([if team[p] == t then elo[p] else 0 endif | p in Players])
                  );

                  % enforce sorted sums to break symmetries
                  % and avoid minimum/maximum predicates
                  constraint forall(t1 in Teams, t2 in Teams where t1 < t2) (
                  eloSums[t1] <= eloSums[t2]
                  );

                  solve minimize eloSums[noOfTeams] - eloSums[1];

                  output ["n "] ++ ["team" ++ show(t) ++ " " | t in Teams] ++
                  ["n"] ++
                  [ if fix(team[p]) != 0 then
                  if t == 1 then
                  "nplayer" ++ show_int(-2,p) ++ " "
                  else
                  ""
                  endif ++
                  if fix(team[p]) == t then
                  show_int(8, elo[p])
                  else
                  " "
                  endif
                  else
                  ""
                  endif
                  | p in Players, t in Teams ] ++
                  ["nsum "] ++
                  [show_int(8, eloSums[t]) | t in Teams ] ++
                  ["navg "] ++
                  [show_float(8,2,eloSums[t]/playersPerTeam) | t in Teams ];


                  The main decision variable is the array team. It assigns every player to one of the teams (0 = no team). To find a close ELO average, I sum up the ELO sums and enforce that minimum and maximum of all team sums are close together.







                  share|improve this answer














                  share|improve this answer



                  share|improve this answer








                  edited Nov 18 at 21:42

























                  answered Nov 18 at 21:13









                  Axel Kemper

                  6,07621742




                  6,07621742



























                      draft saved

                      draft discarded
















































                      Thanks for contributing an answer to Stack Overflow!


                      • Please be sure to answer the question. Provide details and share your research!

                      But avoid


                      • Asking for help, clarification, or responding to other answers.

                      • Making statements based on opinion; back them up with references or personal experience.

                      To learn more, see our tips on writing great answers.





                      Some of your past answers have not been well-received, and you're in danger of being blocked from answering.


                      Please pay close attention to the following guidance:


                      • Please be sure to answer the question. Provide details and share your research!

                      But avoid


                      • Asking for help, clarification, or responding to other answers.

                      • Making statements based on opinion; back them up with references or personal experience.

                      To learn more, see our tips on writing great answers.




                      draft saved


                      draft discarded














                      StackExchange.ready(
                      function ()
                      StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53119389%2fteam-matchmaking-algorithm-based-on-elo%23new-answer', 'question_page');

                      );

                      Post as a guest















                      Required, but never shown





















































                      Required, but never shown














                      Required, but never shown












                      Required, but never shown







                      Required, but never shown

































                      Required, but never shown














                      Required, but never shown












                      Required, but never shown







                      Required, but never shown







                      這個網誌中的熱門文章

                      Barbados

                      How to read a connectionString WITH PROVIDER in .NET Core?

                      Node.js Script on GitHub Pages or Amazon S3