如何告诉正则表达式检查整个子字符串?

Posted

技术标签:

【中文标题】如何告诉正则表达式检查整个子字符串?【英文标题】:How to Tell Regex to Check Whole Sub-String? 【发布时间】:2013-12-04 03:17:24 【问题描述】:

首先是我正在使用的正则表达式:

       String pattern = @"Create(\s+)Table(\s+)(\([a-z0-9]+\))(\s+)Columns(\s+)((\(([a-z0-9]+);(INTEGER|DECIMAL|STRING);(\d1,3);(((YES|NO);)3)([a-z0-9]+)\))+)";
        Match CMD = Regex.Match(Command, pattern, RegexOptions.IgnoreCase);

        if (CMD.Success)
        
            return true;
        

此正则表达式对以下模式按预期工作:

1) 创建表 (MARKS) 列(fountains;StriNg;999;NO;YES;NO;wicked)(rivers;String;500;NO;YES;NO;sweet)

2) 创建表 (MARKS) 列 (ID;Integer;4;YES;YES;YES;0) (riversString;50;NO;YES;NO;sweet)

在第一个模式中,整个字符串是匹配的,但在第二个模式中,只有子字符串 创建表 (MARKS) 列 (ID;Integer;42;YES;YES;YES;0) 匹配

现在它为以下模式返回 false false:

3)创建表 (MARKS) 列 (IDInteger;42;YES;YES;YES;0) (rivers;String;500;NO;YES;NO;sweet)

第二个模式和第三个模式有相同的错误,但唯一的区别是在第二个模式中匹配 \(([a-z0-9]+);(INTEGER|DECIMAL|STRING) ;(\d1,3);(((YES|NO);)3)([a-z0-9]+)\) 在字符串结尾之前已经出现并且因此正则表达式返回 true。

现在我的问题是如何告诉拒绝继续匹配直到字符串结尾?

所以基本上是这样的:不是或除了加号(这意味着一个或多个匹配prevoius)我想要=>一个或多个匹配直到行尾。这样,第三个将导致子字符串 Create Table (MARKS) Columns (rivers;String;500;NO;YES;NO;sweet) 来自 Create Table (MARKS) Columns (IDInteger ;42;YES;YES;YES;0) (rivers;String;500;NO;YES;NO;sweet)

【问题讨论】:

【参考方案1】:

使用开始 (^) 和结束 ($) 符号,例如:

String patter = @"^\d+$";

【讨论】:

是的,我知道这些符号,但只是将它们放在开头或结尾仍然会为第三个模式返回 false? 那么这是主模式的问题,而不是线条边框 是的,主要模式存在问题,这就是为什么要寻求帮助?我尽力解释了这一点【参考方案2】:

\s*? 放在Columns(...) 组的右括号之后,以匹配两个Columns 组之间的0+(惰性)空格:

Create(\s+)Table(\s+)(\([a-z0-9]+\))(\s+)Columns(\s+)((\(([a-z0-9]+);(INTEGER|DECIMAL|STRING);(\d1,3);(((YES|NO);)3)([a-z0-9]+)\)\s*?)+)

最后一个字符串不匹配,因为您忘记了 ID 和整数之间的 ;

编辑:

好的,我明白你需要什么了。

这匹配 Columns 组之间的 0+ 个空格并继续搜索直到找到有效组

Create(\s+)Table(\s+)(\([a-z0-9]+\))(\s+)Columns(\s*\([^)]*\))*(\s*\(([a-z0-9]+);(INTEGER|DECIMAL|STRING);(\d1,3);(((YES|NO);)3)([a-z0-9]+)\))+

查看 RegEx101 http://regex101.com/r/rU6eJ4

编辑 2:

这个只匹配同一行的字符串:

Create[^\S\n]+Table[^\S\n]+(\([a-z0-9]+\))[^\S\n]+Columns([^\S\n]*\([^)]*\))*([^\S\n]*\(([a-z0-9]+);(INTEGER|DECIMAL|STRING);(\d1,3);(((YES|NO);)3)([a-z0-9]+)\))+

【讨论】:

是的,我是故意这样做的....但是子字符串“创建表(标记)列(河流;字符串;500;否;是;否;甜)”与模式匹配,但因为“ (IDInteger;42;YES;YES;YES;0)" 在 "(rivers;String;500;NO;YES;NO;sweet)" 前面,它返回 false,但我希望这种模式(模式 3)为真 所以你需要在第一个;上指定?修饰符 我明白你的意思,我重构了我的代码并完全改变了我的正则表达式......请参阅我的答案。谢谢 @FabioDelarias 我还添加了一个只匹配同一行上的字符串的编辑(\s 也匹配换行符)。【参考方案3】:

不要只使用开始 (^) 和结束 ($) 符号,使用全局修饰符可能会解决这个特定问题。

字符串模式 = @"/^\d+$/g";

【讨论】:

【参考方案4】:

好的,所以基本上我决定将我的正则表达式分解为两个正则表达式:

        String pattern = @"Create(\s+)Table(\s+)(\([a-z0-9]+\))(\s+)Columns(\s+)(((\([a-z0-9;]+\))\s*)+)";
        Match CMD = Regex.Match(Command, pattern, RegexOptions.IgnoreCase);

        if (CMD.Success)
        
            String SubCommand = CMD.Groups[6].Value;
            String SubPattern = @"\(([a-z0-9]+);(INTEGER|DECIMAL|STRING);(\d1,3);(YES|NO);(YES|NO);(YES|NO);([a-z0-9]+)\)";
            MatchCollection match = Regex.Matches(SubCommand, SubPattern, RegexOptions.IgnoreCase);

           if (match.Count != 0)
            
                return true;
            
        

我认为没有很好地解释我的问题,但我感谢大家的帮助

【讨论】:

以上是关于如何告诉正则表达式检查整个子字符串?的主要内容,如果未能解决你的问题,请参考以下文章

使用正则表达式的特定字符串验证

正则表达式(轻松入门级)

正则表达式Regular Expression

正则表达式

如何检查字符串是不是匹配数组中的正则表达式之一?

正则表达式 - 空白无法获取整数值