代码之家  ›  专栏  ›  技术社区  ›  DxCK

string.empty.startswith(((char)10781).toString())始终返回true?

  •  6
  • DxCK  · 技术社区  · 16 年前

    我试图处理以下角色:_( http://www.fileformat.info/info/unicode/char/2a1d/index.htm )

    如果您检查一个以这个字符开头的空字符串,它总是返回true,这没有任何意义!为什么会这样?

    // visual studio 2008 hides lines that have this char literally (bug in visual studio?!?) so i wrote it's unicode instead.
    char specialChar = (char)10781;
    string specialString = specialChar.ToString();
    
    // prints 1
    Console.WriteLine(specialString.Length);
    
    // prints 10781
    Console.WriteLine((int)specialChar);
    
    // prints false
    Console.WriteLine(string.Empty.StartsWith("A"));
    
    // both prints true WTF?!?
    Console.WriteLine(string.Empty.StartsWith(specialString));
    Console.WriteLine(string.Empty.StartsWith(((char)10781).ToString()));
    
    3 回复  |  直到 15 年前
        1
  •  11
  •   RichardOD    16 年前

    您可以使用 ordinal StringComparison :

    来自msdn文档:

    当您指定 StringComparison.Ordinal或 StringComparison.ordinalAlignoreCase, 字符串比较将 非语言。也就是说,功能 那是大自然特有的 制作时忽略语言 比较决定。这意味着 决策基于简单字节 比较并忽略大小写或 等价表是 由区域性参数化。因此, 通过将参数显式设置为 StringComparison.Ordinal或 StringComparison.ordinalAlignoreCase, 你的代码经常加速,增加 正确,并且变得更 可靠。

        char specialChar = (char)10781;
    
    
        string specialString = Convert.ToString(specialChar);
    
        // prints 1
        Console.WriteLine(specialString.Length);
    
        // prints 10781
        Console.WriteLine((int)specialChar);
    
        // prints false
        Console.WriteLine(string.Empty.StartsWith("A"));
    
        // prints false
        Console.WriteLine(string.Empty.StartsWith(specialString, StringComparison.Ordinal));
    
        2
  •  4
  •   Marc Gravell    16 年前

    漂亮的Unicode故障;-p

    我不知道为什么会这样做,但有趣的是:

    Console.WriteLine(string.Empty.StartsWith(specialString)); // true
    Console.WriteLine(string.Empty.Contains(specialString)); // false
    Console.WriteLine("abc".StartsWith(specialString)); // true
    Console.WriteLine("abc".Contains(specialString)); // false
    

    我猜这有点像不加入的角色 Jon mentioned at devdays ;有些字符串函数看到它,有些则看不到。如果看不到它,则会变为“Dos(some string)started with a empty string”,即 总是 是的。

        3
  •  4
  •   Community Mohan Dere    11 年前

    其根本原因是默认的字符串比较具有区域设置意识。这意味着使用区域设置数据表进行比较(包括相等)。

    许多(如果不是大多数)Unicode字符对于许多区域设置都没有值,因此不存在(或不存在,但匹配任何内容或不存在)。

    在迈克尔·卡普兰的博客上看到关于人物重量的条目。” Sorting It All Out “。 This series of blog包含大量的背景信息(API是本地的,但正如我理解的那样.NET中的机制是相同的)。

    快速版本:这是一个复杂的区域,要得到预期的(正常语言)比较是很困难的,这往往会导致一些奇怪的事情,代码点为您的语言之外的字形。