string.IsNullOrEmpty 和 string.IsNullOrWhiteSpace 为空字符串返回 false

Posted

技术标签:

【中文标题】string.IsNullOrEmpty 和 string.IsNullOrWhiteSpace 为空字符串返回 false【英文标题】:string.IsNullOrEmpty & string.IsNullOrWhiteSpace return false for empty string 【发布时间】:2020-05-23 05:05:27 【问题描述】:

我遇到了一个奇怪的案例,在从 MSFT Azure Phrase Breaker 处理一段文本后,一段代码旨在清除空白字符串、句点破折号等。我可以帮助找出如何调试问题。

当给定值"" 时,以下代码块返回true。显然期望是该方法应该在第一个if 语句之后返回false。在要查看的 899 个短语中,似乎只有两个存在这个问题。也发生在另一台机器上。

public static bool IsSentenceTranslatable(string sentence)

    string trimmedSentence = sentence.Trim();

    if (string.IsNullOrEmpty(trimmedSentence) || string.IsNullOrWhiteSpace(trimmedSentence))
    
        return false;
    

    switch (trimmedSentence)
    
        case " ":
        case ".":
        case "-":
        case "·":
            return false;
    

    return true;

这是调试器的快照。

这可能是 Visual Studio 或 .NET 中的错误吗?我尝试使用各种可视化工具,但仍然看不到盒子里的任何东西。 .NET 4.5 C# 7.3

【问题讨论】:

可能是zero-width space? trimmedSentence.Length 的值为 1 不是已经在告诉您该字符串确实是非空的吗?你试过检查trimmedSentence[0]的值吗? 顺便说一句:在 120% 的情况下,我认为某些事情是“……Vis​​ual Studio 或 .NET 中的错误……”,结果证明是我的错。 阅读here。从示例网站复制文本后,您的字符串包含不可见字符。 @Andrew 我的问题是如何调试它,trimmedSentence[0] 成功解锁了正确的谷歌搜索。如果您提交答案,则将其标记为已批准。 【参考方案1】:

尝试获取字符串的字节表示。我怀疑它实际上包含一些在 VS 调试器中不可见但不算作空格的字符。

请参阅此问题以获取提示:

Invisible characters - ASCII Converting string to byte array in C#

UPD:由于您的“监视”窗口显示在呼叫 string trimmedSentence = sentence.Trim() 后您拥有trimmedSentence.Length == 1,因此我将怀疑升级为确定性。

【讨论】:

我很欣赏这个答案,但它只告诉你你已经知道的。请参阅接受的答案,它会告诉您如何实际确定下一步。 @TaylorAckley 如果您已经知道这一点,为什么还要问“这可能是 Visual Studio 或 .NET 中的错误”? 我认为那里一定有什么东西,但为什么我必须对字符串进行一些操作才能看到一些东西?似乎其中一个可视化工具应该显示一些东西,特别是如果它有一个实体代码并且您在 html 可视化工具中查看它。也许不是一个错误,但会有助于他们向您展示除空引号和空白可视化器之外的其他内容。【参考方案2】:

正如我在评论中所说,在该屏幕截图中您可以看到trimmedSentence.Length 为1,因此它不是空的,其内容绝对不是标准空格。如果字符串显示为空,那是因为它具有那些所谓的不可见字符之一。要检查您的字符串有什么,您可以通过 trimmedSentence[0] 直接访问该字符。

如果该字符经常出现,您可能需要考虑这样做:

string trimmedSentence = sentence.Trim().Replace("<this special character>", "");

或者,您可以通过执行Char.ConvertFromUtf32(yourCharCode).ToString() 从 Unicode 值创建可替换字符串。您不能使用使用字符参数的Replace 重载,因为没有“空”字符,只有一个空字符串。您应该能够在调试时获得此值。或者,如有必要,请通过 (int)trimmedSentence[0]

【讨论】:

FWIW - 当您检查字符串中的第一个字符时(即trimmedSentence[0],它可能看起来像一个带引号的随机数。Google 无引号的数字,您将获得 ascii 代码。 顺便说一句,它的价值是多少?通常它们以十六进制显示,您可以使用((int)trimmedSentence[0]).ToString("X") 来获取这个不可见空间的十六进制表示。

以上是关于string.IsNullOrEmpty 和 string.IsNullOrWhiteSpace 为空字符串返回 false的主要内容,如果未能解决你的问题,请参考以下文章

String.IsNullOrEmpty()和String.IsNullOrWhiteSpace()

使用 String.IsNullOrEmpty(string) 和 Nhibernate 创建动态 Linq 表达式

string.IsNullOrEmpty 和 string.IsNullOrWhiteSpace 为空字符串返回 false

String.IsNullOrEmpty()和String.IsNullOrWhiteSpace()的区别

WiFi热点

为什么String.IsNullOrEmpty(str)而不是str.IsNullOrEmpty()?