我需要从字符串中提取一组包含在两个分隔符之间的字符,而不返回分隔符本身。
一个简单的例子应该会有所帮助:
目标:提取方括号之间的子字符串,而不返回括号本身。
基本字符串:This is a test string [more or less]
如果我使用以下注册。前任。
\[.*?\]
匹配是 [more or less]
。我只需要得到 more or less
(不带括号)。
有可能做到吗?
轻松搞定:
(?<=\[)(.*?)(?=\])
从技术上讲,这是使用前瞻和后瞻。请参阅Lookahead and Lookbehind Zero-Width Assertions。该模式包括:
前面有一个 [ 未捕获(向后看);
一个非贪婪的捕获组。停在第一个 ] 是非贪婪的;和
后跟一个未捕获的 ](前瞻)。
或者,您可以只捕获方括号之间的内容:
\[(.*?)\]
并返回第一个捕获的组而不是整个匹配。
如果您使用 JavaScript,cletus 提供的 solution,(?<=\[)(.*?)(?=\])
将不起作用,因为 JavaScript 不支持后向运算符。
编辑:实际上,now (ES2018) 可以使用后向运算符。只需添加 / 来定义正则表达式字符串,如下所示:
var regex = /(?<=\[)(.*?)(?=\])/;
老答案:
解决方案:
var regex = /\[(.*?)\]/;
var strToMatch = "This is a test string [more or less]";
var matched = regex.exec(strToMatch);
它将返回:
["[more or less]", "more or less"]
所以,你需要的是第二个值。利用:
var matched = regex.exec(strToMatch)[1];
返回:
"more or less"
您只需要“捕获”括号之间的位。
\[(.*?)\]
为了捕捉你把它放在括号内。你没有说这是使用哪种语言。例如,在 Perl 中,您可以使用 $1 变量来访问它。
my $string ='This is the match [more or less]';
$string =~ /\[(.*?)\]/;
print "match:$1\n";
其他语言会有不同的机制。例如,我相信 C# 使用 Match collection 类。
这是一个带有明显分隔符(X
和 Y
)的一般示例:
(?<=X)(.*?)(?=Y)
这里用于查找 X
和 Y
之间的字符串。 Rubular 示例 here,或参见图片:
https://i.stack.imgur.com/jE62L.png
[^\[]
匹配任何不是 [.
+
匹配 1 个或多个不是 [
的内容。创建这些匹配的组。
(?=\])
积极前瞻]
。匹配以 ]
结尾的组,但不将其包含在结果中。
完毕。
[^\[]+(?=\])
证明。
类似于null提出的解决方案。但不需要额外的 \]
。作为附加说明,似乎 \
不需要在 ^
之后转义 [
。为了可读性,我会把它留在里面。
在分隔符相同的情况下不起作用。 "more or less"
例如。
[^\[\]]+(?=\])
PHP:
$string ='This is the match [more or less]';
preg_match('#\[(.*)\]#', $string, $match);
var_dump($match[1]);
最新的解决方案
如果您使用的是 Javascript,我想出的最佳解决方案是使用 match
而不是 exec
方法。然后,使用 $1
迭代匹配并使用第一组的结果删除分隔符
const text = "This is a test string [more or less], [more] and [less]";
const regex = /\[(.*?)\]/gi;
const resultMatchGroup = text.match(regex); // [ '[more or less]', '[more]', '[less]' ]
const desiredRes = resultMatchGroup.map(match => match.replace(regex, "$1"))
console.log("desiredRes", desiredRes); // [ 'more or less', 'more', 'less' ]
如您所见,这对于文本中的多个分隔符也很有用
这个特别适用于 javascript 的正则表达式解析器 /[^[\]]+(?=])/g
只需在控制台中运行它
var regex = /[^[\]]+(?=])/g;
var str = "This is a test string [more or less]";
var match = regex.exec(str);
match;
我在使用带有 bash 脚本的正则表达式时遇到了同样的问题。我使用了带有 grep -o 应用的管道的两步解决方案
'\[(.*?)\]'
首先,然后
'\b.*\b'
显然在其他答案上效率不高,而是另一种选择。
我想在 / 和 # 之间找到一个字符串,但 # 有时是可选的。这是我使用的正则表达式:
(?<=\/)([^#]+)(?=#*)
以下是我在 C# 中没有 '['
和 ']'
的情况:
var text = "This is a test string [more or less]";
// Getting only string between '[' and ']'
Regex regex = new Regex(@"\[(.+?)\]");
var matchGroups = regex.Matches(text);
for (int i = 0; i < matchGroups.Count; i++)
{
Console.WriteLine(matchGroups[i].Groups[1]);
}
输出是:
more or less
如果需要提取不带括号的文本,可以使用 bash awk
echo " [hola mundo] " | awk -F'[][]' '{print $2}'
结果:
hola mundo
This is a test string [more [or] less]
中会返回more [or] less
吗?