【问题标题】:Best way to compare two strings ignoring case [closed]比较两个字符串忽略大小写的最佳方法[关闭]
【发布时间】:2016-10-06 06:51:11
【问题描述】:

我想比较两个不区分大小写的字符串,但我不确定最好的方法。字符串的平均长度为 20,这个问题更多的是关于最先进的技术,而不是关于最佳性能

我的大部分代码都使用了

bool output = "foo".ToLower() == "FOO".ToLower();

这对我来说似乎有点过时了。另一种我见过很多次的方式是

bool output = Regex.IsMatch("foo", "FOO", RegexOptions.IgnoreCase);

我想这是可能的,但 RegEx 不适合这么简单的事情。

之后剩下3条“好”的方式:

bool output = string.Compare("foo", "FOO", StringComparison.CurrentCultureIgnoreCase) == 0;
bool output = string.Compare("foo", "FOO", true) == 0;
bool output = "foo".Equals("FOO", StringComparison.CurrentCultureIgnoreCase);

【问题讨论】:

  • 这是一个基于意见的问题。但在我看来:string.Equals("x", "y", StringComparison.OrdinalIgnoreCase)
  • 源索引不是一个选项?
  • 也看herehere
  • “最好的”是什么意思?最佳性能、最短、最易读?
  • @NikaGamkrelidze 都在第二句中说了

标签: c# string


【解决方案1】:

如果你看看相应的参考来源

https://referencesource.microsoft.com/#mscorlib/system/string.cs,bda3b2c94b5251ce

    public static int Compare(String strA, String strB, bool ignoreCase)
    {
        if (ignoreCase) {
            return CultureInfo.CurrentCulture.CompareInfo.Compare(strA, strB, CompareOptions.IgnoreCase);
        }
        return CultureInfo.CurrentCulture.CompareInfo.Compare(strA, strB, CompareOptions.None);
    }

https://referencesource.microsoft.com/#mscorlib/system/string.cs,0be9474bc8e160b6

    public static int Compare(String strA, String strB, StringComparison comparisonType) 
    {
    ... 
        // Agrument validation, reference equality, null test

        switch (comparisonType) {
        ...
           case StringComparison.CurrentCultureIgnoreCase:
                return CultureInfo.CurrentCulture.CompareInfo.Compare(strA, strB, CompareOptions.IgnoreCase);

https://referencesource.microsoft.com/#mscorlib/system/string.cs,d47c1f57ad1e1e6e

    public static bool Equals(String a, String b, StringComparison comparisonType) {
    ... 
       // Agrument validation, reference equality, null test

       switch (comparisonType) {
        ...
           case StringComparison.CurrentCultureIgnoreCase:
                return (CultureInfo.CurrentCulture.CompareInfo.Compare(a, b, CompareOptions.None) == 0);

您会发现这三种方法彼此相等。至于其他方式,Regex.IsMatch 绝对是overshoot(你要做的就是比较字符串); ToLower() 在处理特定于文化的字母时可能会很棘手,请参阅

https://en.wikipedia.org/wiki/Dotted_and_dotless_I

这就是为什么更好的设计是清楚地声明你的意图(=我想比较字符串)然后屏蔽它们(让系统欺骗你)

【讨论】:

    【解决方案2】:

    如果您要检查是否相等,请使用Equals。使用Compare 相当于使用

    if (collection.Count() == 0)
    

    而不是

    if (collection.Any())
    

    在 LINQ 中。即使这两者目前可以实现并执行相似,您也掩盖了您的意图,并且您无法保证将来会出现这种情况。

    【讨论】:

    • Compare 也确定了排序顺序 (-1,0,1) 而Equals 只是检查相等性对吗?
    • 没错。如果您关心两个项目是否相等,您应该调用检查它们是否相等的方法,而不是检查一个大于或小于另一个的方法。
    【解决方案3】:

    我觉得不错

    bool output = Regex.IsMatch("foo", "FOO", RegexOptions.IgnoreCase);
    

    【讨论】:

    • 我认为正则表达式是你应该考虑的最后一件事,只有当所有其他方法都失败时它才是好的。这表明这个问题是基于意见的,因此在这里偏离主题
    猜你喜欢
    • 1970-01-01
    • 2016-01-29
    • 2018-02-10
    • 1970-01-01
    • 2011-09-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-04-10
    相关资源
    最近更新 更多