是否可以在正则表达式中跳过捕获组中的几个字符?我正在使用.NET正则表达式,但这无关紧要。
基本上,我要找的是:
[随机文本] AB-123 [随机文本]
我需要捕捉'AB123',不带连字符。
我知道AB是2或3个大写字符,123是2或3位数,但这不是困难的部分。困难的部分(至少对我而言)正在跳过连字符。
我想我可以单独捕获它们然后在代码中连接它们,但我希望我有一个更优雅的,仅正则表达式的解决方案。
有什么建议吗?
答案 0 :(得分:45)
简而言之:你做不到。匹配总是连续的,即使它包含零宽度断言的东西,如果你想要到达后一个字符,也无法匹配下一个字符。
答案 1 :(得分:17)
确实无法创建表达式,以使匹配的文本与源文本中找到的文本不同。您需要在单独的步骤中删除连字符,方法是分别匹配第一个和第二个部分并连接两个组:
match = Regex.Match( text, "([A-B]{2,3})-([0-9]{2,3})" );
matchedText = string.Format( "{0}{1}",
match.Groups.Item(1).Value,
match.Groups.Item(2).Value );
或者通过在与匹配过程分开的步骤中删除连字符:
match = Regex.Match( text, "[A-B]{2,3}-[0-9]{2,3}" );
matchedText = match.Value.Replace( "-", "" );
答案 2 :(得分:4)
你断言如果没有子分组+连接就不可能做到这一点是正确的。
你也可以像杰夫 - 希尔曼那样做,并且只是在事后删除了坏人物。
重要的是要注意这里,你是“不要用正则表达式”。
正则表达式是针对非平凡问题的不太复杂的解决方案而设计的,你不应该使用“哦,我们将使用正则表达式”来做所有事情,你不应该进入认为可以解决问题的习惯。一步法正则表达式中的问题。
当有一个可行的琐碎方法有效时,一定要使用它。
另一个想法,如果您碰巧需要在代码体中返回多个匹配项,那么请查找基于正则表达式的语言“回调”,它允许将任何匹配/找到的组传递给函数调用,该函数调用可以在 - 换行。 (在进行正则表达式替换时特别方便)。
不确定它在.Net中是如何工作的,但是在php中你会做类似的事情(不是确切的代码)
function strip_reverse( $a )
{
$a = preg_replace("/-/", "", $a );
return reverse($a);
}
$b = preg_replace_callback( "/(AB[-]?cde)/" , 'strip_reverse' , "Hello World AB-cde" ;
答案 3 :(得分:1)
您可以使用嵌套捕获组,如下所示:
((AB)-(123))
第一个捕获组是AB-123
,第二个是AB
,第三个是123
。然后你所要做的就是用空格加入第二组和第三组。
答案 4 :(得分:0)
有点晚了,但我想我想出了这个。至少有一种方法可以做到。
我使用积极的预测来停留在我的文字中的#符号。我不想要空格或#符号,所以我不得不想办法“跳过”它们。因此,当我被迫再次匹配它们时,我将它们转储到我不打算使用的垃圾组(.ie,有点桶),代码就是这样。现在,我的位置指针是#符号之外的一个字符位置(我想要的位置,跳过空格和#符号)。我现在只匹配文件名的末尾。并忽略文件扩展名。
(?i)English\\(?<Series>[^ ]+) - (?<Title>.+(?= #))(?<garb1>..)(?<Number>[^.]+)(?-i)
使用的文件名是
F:\Downloads\Downloads\500 Comics CCC CBR English\Isukani - Great Girl #01.cbr
答案 5 :(得分:0)
对此我有点陌生,但是您可以使用竖线符号import { ToastrService } from 'ngx-toastr';
export class AppComponent {
constructor(private toastr: ToastrService) { }
showSuccess() {
this.toastr.success('Success', 'Toastr fun!', {
timeOut: 200000,
positionClass: 'toast-bottom-right' // <-- set position here
});
}
}
,它用作OR。
这可能适用于.NET:
|
这在VIM语法文件中对我有用:
((?<=[A-Z]{2}-)\d\d\d)|([A-Z]{2}(?=-\d\d\d))