C# - 公平的团队分配与评级

时间:2016-02-13 22:09:56

标签: c# list rating

我有一个体育运动员的排名列表,并希望将它们分配给团队,以便评级的分布尽可能公平(即,消除具有大量高评级玩家的团队,反之亦然)。

目前我正在这样做,但它似乎没有提供最佳解决方案:

ratingList.Sort();
ratingList.Reverse();

var team1List = ratingList.Where((r, i) => i % 2 != 0).ToList();
var team2List = ratingList.Where((r, i) => i % 2 == 0).ToList();

2 个答案:

答案 0 :(得分:1)

按降序排序后,试试这个

var team1List = ratingList.Where((r, i) => i % 2 != 0).ToList();
var team2List = ratingList.Where((r, i) => i % 2 == 0).ToList();

答案 1 :(得分:0)

对于最佳解决方案,我们的想法是并排考虑ratingList两次 ascending vs descending并采取前半部分(另一部分只是镜像)

Ex:
0, 1, 2, 3, 4 | 5, 6, 7, 8, 9
9, 8, 7, 6, 5 | 4, 3, 2, 1, 0

and keep the first half

team1 team2 team1 team2 |
0,    1,    2,    3,    | 4 team1
9,    8,    7,    6,    | 5 team2

evens进入team1team2的赔率。如果我们有偶数对,最后一对将在两个团队之间重新分配(另请注意,这仅适用于ratingList >= 4(由您来处理更少)。甚至我建议排除中间评级的评级数量,以及稍后决定如何处理它。

考虑到以上所有问题,解决方案应如下所示

ratingList.Sort();
var count = ratingList.Count();

// if even number of players, keep aside the one in the middle (as rating)
int? middle = null;
if (count % 2 != 0)
{
    middle = ratingList[count / 2];
    ratingList.RemoveAt(count / 2);
}

var ratingListDesc = ratingList.OrderByDescending(i => i).ToList();

var half = count / 2;
var take = half % 2 != 0 ? half - 1 : half;

var team1List = ratingList.Take(take).Where((r, i) => i % 2 == 0).ToList();
team1List.AddRange(ratingListDesc.Take(take).Where((r, i) => i % 2 == 0));

var team2List = ratingList.Take(take).Where((r, i) => i % 2 != 0).ToList();
team2List.AddRange(ratingListDesc.Take(take).Where((r, i) => i % 2 != 0));

// we just have to redistribute the remaining pair between each team
if (half % 2 != 0)
{
     team1List.Add(ratingList[half - 1]);
     team2List.Add(ratingListDesc[half - 1]);
}

if (middle.HasValue)
{
    // do something, or not ...
}