将LINQ orderby转换为inplace list sort

Geo*_*ett 5 c# linq sorting list

目前,我正在使用LINQ对象对列表进行排序,然后ToList()对结果进行处理:

var SortedPossibleMoveLocations = (from PML in PossibleMoveLocations
                                   orderby Randomiser.Next()
                                   orderby IsSameType(PML) ? (_Owner[PML] as TileFlowing).UnitsWithin : 0
                                   orderby PossibleMoveLocationOrdering(PML)
                                   select PML).ToList();
Run Code Online (Sandbox Code Playgroud)

我想转换它来做一个inplace sort,我想使用List<T>.Sort()方法.如果我只是按一个事情排序,我知道如何做到这一点,但是,因为我按顺序排序PossibleMoveLocationOrdering(返回一个int)然后通过IsSameType(PML) ? (_Owner[PML] as TileFlowing).UnitsWithin : 0哪个计算结果为a int,然后通过Randomiser.Next()(返回一个随机int)我不这样做知道怎么做.

问题:如何编写比较函数(或者有更好的方法)来执行上面的LINQ查询.

Jon*_*eet 11

首先,指定三个orderby子句是个坏主意 - 而是仅使用逗号分隔指定多个排序.

我也不热衷于使用Randomiser.Next()订购的想法,但这是一个不谈.

您的LINQ查询应该如下所示(目前仍在使用Randomiser中):

var query = (from PML in PossibleMoveLocations
             orderby PossibleMoveLocationOrdering(PML),
                     IsSameType(PML) ? (_Owner[PML] as TileFlowing).UnitsWithin : 0,
                     Randomiser.Next()
             select PML).ToList();
Run Code Online (Sandbox Code Playgroud)

就个人而言,我只是使用点符号:

var query = PossibleMoveLocations
                .OrderBy(pml => PossibleMoveLocationOrdering(PML))
                .ThenBy(pml => IsSameType(pml) ? 
                                    (_Owner[pml] as TileFlowing).UnitsWithin : 0)
                .ThenBy(pml => Randomiser.Next())
                .ToList();
Run Code Online (Sandbox Code Playgroud)

要进行排序,您基本上需要一个Comparison<T>IComparer<T>哪个可以测试多个东西,还有一个使用属性创建比较器的实现.你可以手动完成(按照Marc的代码),但是当它发生时,我在MiscUtil中有一些帮助类和扩展方法:

var comparer = ProjectionComparer<PossibleMove>
                   .Create(pml => PossibleMoveLocationOrdering(PML));
                   .ThenBy(pml => IsSameType(pml) ? ...)
                   .ThenBy(...);

list.Sort(comparer);
Run Code Online (Sandbox Code Playgroud)

请注意,使用Randomizer这里绝对是一个坏主意,因为它会在每个比较(与相等的第一件物品)被称作......这可能会导致不一致的比较,从而x< y< z< x.


Mar*_*ell 6

最常见的:

list.Sort((x,y) => {
    int result = /* first comparison, for example
                    string.Compare(x.Name, y.Name) */
    if (result == 0) result = /* second comparison,
                                 for example x.Id.CompareTo(y.Id) */
    ...
    if (result == 0) result = /* final comparison */
    return result;
});
Run Code Online (Sandbox Code Playgroud)

或类似的(可能在比较者类中,如果它是非平凡的).