使用 LINQ Orderby 的 ORDER 字符串

问题描述 投票:0回答:1

请考虑此代码:

string str1 = "M"; // <---77
string str2 = "m"; // <---109

var list = new List<string>() {str1, str2};

list = list.OrderBy(a=>a).ToList();

问题是尽管

m
有更大的ascii代码,但它却在
M
之前。为什么会发生在这里?

LINQ 使用什么类型的比较进行排序以及如何更改它?

c# string linq
1个回答
0
投票

如果未指定比较器,

OrderBy
将使用
Comparer<T>.Default
获取比较器。最终,这似乎解决了
GenericComparer<T>
,它使用
string
CompareTo
方法。如果您想深入了解代码,可以从here开始查看。

根据我在

StringComparer.InvariantCulture
的文档中的内容,似乎
m
M
之前是“语言相关”顺序,所以我假设其他文化敏感的英语比较器也假设相同订购。

至于如何按照您想要的方式排序,您可以为

OrderBy
方法指定一个比较器(内置或自定义)。例如:
list.OrderBy(a => a, StringComparer.InvariantCulture)
(但可能不是这个比较器)。

我不知道有哪个特定的比较器可以按照您想要的方式对其进行排序,因此您可能需要创建一个类似于这样的自定义比较器:

自定义字符串比较器的简单示例

public class CustomStringComparer : IComparer<string>
{
    private static readonly CustomStringComparer _instance = new CustomStringComparer();
    public static CustomStringComparer Instance => _instance;

    private CustomStringComparer() { }

    public int Compare (string x, string y)
    {
        if (string.Equals(x, y)) 
        {
            return 0;
        }
           
        int minLength = Math.Min(x.Length, y.Length);
        for (int i = 0; i < minLength; ++i)
        {
            var compareResult = ((int)x[i]).CompareTo(y[i]);
            if (compareResult != 0)
            {
                return compareResult;
            }
        }
        return 0;
    }
}

这只是一个基于您想要比较 ASCII 代码的隐含愿望的示例。我预计它不能很好地处理很多情况,因此如果您希望它完全按照您的需要进行操作,您可能需要对其进行更改。

用途:

list = list.OrderBy(a => a, CustomStringComparer.Instance).ToList();
© www.soinside.com 2019 - 2024. All rights reserved.