Regex replace commas within parentheses C#

后端 未结 2 841
一向
一向 2021-01-27 03:52

I\'m having a hell of a time replacing commas only within parentheses for this string:

select distinct \\n(\'\'+rtrim(ent.custno)+\' - \'+rtrim(ent.com

相关标签:
2条回答
  • 2021-01-27 04:06

    Assuming your parentheses are paired and can be nested (balanced), and you need to replace all commas inside those balanced parentheses, you can use a regex to match those substrings and replace the commas with a match evaluator:

    cols = Regex.Replace(cols, @"\((?>[^()]|(?<c>)\(|(?<-c>)\))*(?(c)(?!))\)", m => m.Value.Replace(",", ";"));
    

    See IDEONE demo

    0 讨论(0)
  • 2021-01-27 04:19

    The problem is that your string contains nested parenthesis. Your pattern must take in account this fact and describe eventual nested parenthesis like in this example string: (aaaaa,bbbbb(cccc(ffffdd)eeee)ffff) to be sure that the closing parenthesis is the good one.

    string pattern = @",(?=(?>[^()]+|\((?<depth>)|\)(?<-depth>))*?(?(depth)(?!))\))";
    cols = Regex.Replace(cols, pattern, ";");
    

    Named captures (that captures nothing here) act like a counter.

    Each time an opening parenthesis is encountered, the counter is incremented, and each time a closing parenthesis is encountered, the counter is decremented. At the end, the conditional (?(depth)...) checks the counter (named depth in the example) and if it is not null, it forces the pattern to fail with the always failing assertion: (?!) (literally: not followed by nothing).

    details:

    ,
    (?=
        (?>                 # open an atomic group: important because a simple 
                            # non-capturing group(?:[^()]+)* may cause a catastrophic
                            # backtracking if the end of the pattern doesn't succeed.
    
            [^()]+          # all that is not a parenthesis
          |
            \( (?<depth>)   # a opening parenthesis increments the counter
          |
            \) (?<-depth>)  # a closing parenthesis decrements the counter
        )*?                 # a non-greedy quantifier is used because the group must
                            # be repeated until the end of the pattern succeeds
                            # (it prevents the regex engine to match all the string
                            # and to give back characters until the pattern succeeds)
    
        (?(depth) (?!) )    # check the counter and forces to fail when not null
        \)
    )
    
    0 讨论(0)
提交回复
热议问题