【问题标题】:How would I remove all commas not inside parenthesis from a string in C#?如何从 C# 中的字符串中删除所有不在括号内的逗号?
【发布时间】:2009-05-07 21:38:43
【问题描述】:

我有一个可以执行“IntPow(3,2)”之类的函数的数学解析器。如果用户粘贴“1,000,000”,然后添加一个加号,使完整的等式“1,000,000+IntPow(3,2)”解析器失败,因为它不适用于包含逗号的数字。

我需要从“1,000,000”中删除逗号,而不是从“IntPow(3,2)”中删除逗号,因为 IntPow 有两个由逗号分隔的参数。最终等式将是“1000000+IntPow(3,2)”。方程式存储在一个字符串中。如何仅删除括号外的逗号?我假设并说包含逗号的数字不会放在 IntPow 参数列表中。

当我说“删除逗号”时,我的意思是删除“CultureInfo.CurrentCulture.NumberFormat.NumberGroupSeparator”,这可能是逗号或句点,具体取决于本地。这部分很简单,因为我假设将使用 RegEx,我可以在 RegEx 逗号位置连接该值。

我有这个 RegEx: (.*?) 用于在其中查找括号和值,但我不确定如何仅删除 RegEx 匹配项之外的逗号。

【问题讨论】:

  • 您是否假设所有括号都是余额,即每个 '(' 都有一个匹配的 ')'?

标签: c# regex


【解决方案1】:

最简单的方法是不要尝试使用正则表达式来执行此操作。一次只循环一个字符。如果你读到一个'(',增加一个计数器。如果你读到一个')',减少那个计数器。如果读到逗号,如果计数器为 0,则将其删除,否则不理会。​​p>

【讨论】:

    【解决方案2】:

    但是如果用户粘贴怎么办:

    1,000+IntPow(3,000,2,000)
    

    现在 3,000 在逗号之间。

    【讨论】:

    • 这可能不起作用,因为 IntPow() 函数不接受四个参数。
    • 解析器在到达 IntPow 函数之前会中断 1,000。括号内的数字也可以是逗号数字分组格式。
    • 问题中提到了这一点:“我假设并说包含逗号的数字不会放在 IntPow 参数列表中。”。我的意思是,如果是这种情况,那么它就不会计算,我可以接受。
    【解决方案3】:
    Sub Main()
    
        '
        '   remove Commas from a string containing expression-like syntax
        '       (eg.  1,000,000 + IntPow(3,2) - 47 * Greep(9,3,2) $ 5,000.32 )
        '       should become:  1000000 + IntPow(3,2) - 47 * Greep(9,3,2) $ 5000.32
        '
    
        Dim tInput As String = "1,000,000 + IntPow(3,2) - 47 * Greep(9,3,2) $ 5,000.32"
        Dim tChar As Char = Nothing
        Dim tResult As StringBuilder = New StringBuilder(tInput.Length)
        Dim tLevel As Integer = 0
    
        For Each tChar In tInput
            Select Case tChar
                Case "("
                    tLevel += 1
                    tResult.Append(tChar)
    
                Case ")"
                    tLevel -= 1
                    tResult.Append(tChar)
    
                Case ","   '  Change this to your separator character.
                    If 0 < tLevel Then
                        tResult.Append(tChar)
                    End If
    
                Case Else
                    tResult.Append(tChar)
    
            End Select
        Next
    
        Console.ForegroundColor = ConsoleColor.Cyan
        Console.WriteLine(tInput)
        Console.WriteLine(String.Empty)
        Console.ForegroundColor = ConsoleColor.Yellow
        Console.WriteLine(tResult.ToString)
        Console.WriteLine()
        Console.ResetColor()
        Console.WriteLine(" -- PRESS ANY KEY -- ")
        Console.ReadKey(True)
    
    End Sub
    

    【讨论】:

    • Chad Birch 得到了答案,您提供了示例代码。太糟糕了,我不能同时选择两者。在这种情况下,我将不得不将解释作为最佳答案,因为它解释了它是如何完成的(代码也是如此,但单词更通用)。我仍然会稍微投票这个答案。
    【解决方案4】:

    我认为使用正则表达式是不可能的。区分内括号和外括号不是常规语言。它是一种上下文不敏感的语言,无法使用常规状态机(表达式)来决定。您需要一台堆栈机(即由乍得决定的链接)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2023-04-11
      • 1970-01-01
      • 2021-03-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多