【问题标题】:Match numbers that not in context of Value(x)匹配不在 Value(x) 上下文中的数字
【发布时间】:2021-11-22 16:36:06
【问题描述】:

我正在尝试匹配不在 Value(X) 上下文中的数字并丢弃其余文本。

示例文本:

 lorem ipsum Value (3) dfasdf 654345435ds sdfsdf asdf
asd
F
asdf
sad Value (2)

正则表达式示例:

 Value\((\d)\)

感谢您的帮助。

【问题讨论】:

    标签: c# .net regex


    【解决方案1】:

    .NET 正则表达式引擎支持后向断言中的量词。

    您可以做的是断言从当前位置开始,左边不是有 1 个以上数字的 Value(,右边是 )。如果是这种情况,请匹配 1 个或多个数字。

    模式匹配:

    (?<!\bValue[\p{Zs}\t]*\((?=[0-9]+\)))[0-9]+
    
    • (?&lt;! 正面向后看,断言左边是
      • \bValue 匹配 Value 前面有一个单词边界以防止部分匹配
      • [\p{Zs}\t]*\( 匹配可选的水平空格,后跟(
      • (?=[0-9]+\)) 正向前瞻,断言 1+ 数字后跟 ) 向右
    • ) 近距离观察
    • [0-9]+ 匹配 1+ 位 0-9

    .NET regex demo

    请注意,\d 仅匹配 0-9 以外的数字,还匹配其他语言的数字。如果要匹配,可以使用\d,否则可以使用[0-9]

    【讨论】:

    • @AaronPanVega - 欢迎您,很高兴它对您有用。如果它有助于解决问题,请随时mark the answer,点击答案左侧的✓。
    【解决方案2】:

    您正在寻找:

    (?<!Value *\()\d+)
    

    请注意,我假设每个 Value( 都有一个右括号。

    说明:

    • (?&lt;!Value *\() 断言其后面没有"Value("Value (Value ( 等。
    • \d+ 匹配一次到无限次之间的数字

    【讨论】:

    • 不,您的正则表达式不符合您的解释。您的(?!&lt;Value *\()\d+(?!\)) 正则表达式等于\d+(?!\))(任何一个或多个数字,其中最后一个数字后面没有紧跟)),因为(?!&lt;Value *\() 是向前看,而不是向后看。
    • 抱歉,错误地交换了!&lt;。现已修复。
    • 但是现在,(34) 中的 (?&lt;!Value *\()\d+(?!\)) will match 3,而不是预期的 34。这不符合只忽略一个特定上下文的要求。
    • 所以...不需要负前瞻?
    • 不,两者都是必需的,或者不是,取决于使用什么方法,方法取决于 OP 想要/打算做什么,在我们知道之前,我们无法回答。跨度>
    【解决方案3】:

    你应该这样做:

    private static readonly Regex rx = new Regex(@"
      (?<!          # A zero-width negative look-behind assertion, consisting of:
        \w          #   - a word boundary, followed by
        Value       #   - the literal 'Value', followed by
        \s*         #   - zero or more whitespace characters, followed by
        [(]         #   - a left parenthesis '(', followed by
        \s*         #   - zero or more whitespace characters,
      )             # The whole of which is followed by
      (             # A number, consisting of
        -?          #   - an optional minus sign, followed by
        \d+         #   - 1 or more decimal digits,
        )           # The whole of which is followed by
      (?!           # A zero-width negative look-ahead assertion, consisting of
        \s*         #   - zero or more whitespace characters, followed by
        [)]         #   - a single right parenthesis ')'
      )             #
    ",
        rxOpts
      );
    
    private const RegexOptions rxOpts = RegexOptions.IgnoreCase
                                      | RegexOptions.ExplicitCapture
                                      | RegexOptions.IgnorePatternWhitespace
                                      ;
    

    然后。 . .

    foreach ( Match m in rx.Matches( someText ) )
    {
      string nbr = m.Value;
      Console.WriteLine("Found '{0}', nbr);
    }
    

    【讨论】:

      猜你喜欢
      • 2019-08-21
      • 2020-10-13
      • 2016-07-11
      • 2014-01-12
      • 2023-03-03
      • 2016-10-14
      • 2013-03-27
      • 2019-10-27
      • 2022-08-20
      相关资源
      最近更新 更多