我的值是这样的:
"Foo Bar" "Another Value" something else
什么正则表达式将返回括在引号中的值(例如Foo Bar和Another Value)?
我的值是这样的:
"Foo Bar" "Another Value" something else
什么正则表达式将返回括在引号中的值(例如Foo Bar和Another Value)?
当前回答
我的解决方案如下
(\[‘])。* 1 (? ! [s ^ \])
演示链接:https://regex101.com/r/jlhQhV/1
解释:
(["'])->匹配'或',一旦找到匹配,将其存储在反向引用\1中
.* ->贪婪的方法继续匹配所有内容0次或更多次,直到它在字符串末尾遇到'或"。遇到这种状态后,正则表达式引擎返回到上一个匹配字符,此时正则表达式结束,将移动到下一个正则表达式。
\1 ->匹配先前与第一个捕获组匹配的字符或字符串。
(?![^\s]) ->负前向,确保在之前的匹配之后不应该有任何非空格字符
其他回答
我能够创建这个正则表达式来满足我的需求。
我需要匹配一个包含引号的特定值。它必须是完全匹配的,没有部分匹配可以触发命中
如。“test”不能与“test2”匹配。
reg = r"""(['"])(%s)\1"""
if re.search(reg%(needle), haystack, re.IGNORECASE):
print "winning..."
猎人
echo 'junk "Foo Bar" not empty one "" this "but this" and this neither' | sed 's/[^\"]*\"\([^\"]*\)\"[^\"]*/>\1</g'
这将导致:>Foo Bar<><>但这<
在这里,为了清晰起见,我显示了><'s之间的结果字符串,也使用了这个sed命令的非贪婪版本,我们首先抛出' 's之前和之后的垃圾,然后用' ' 's之间的部分替换它,并用><'s包围它。
我一直在使用以下方法并取得了巨大的成功:
(["'])(?:(?=(\\?))\2.)*?\1
它还支持嵌套引号。
对于那些想要更深入地解释这是如何工作的人,这里是用户ephemerent的解释:
([""'])匹配引号;((?=(\\?))\2.)如果存在反斜杠,吞噬它,无论是否发生,匹配一个字符;* ?匹配多次(非贪婪,如不吃结尾引号);\1匹配相同的报价,是用于开幕。
让我们看看处理转义引号的两种有效方法。这些模式不是为了简洁或美观而设计的,而是为了高效。
这些方法使用第一个字符区分快速查找字符串中的引号,而不需要进行替换。(这个想法是快速丢弃不是引号的字符,以测试交替的两个分支。)
引号之间的内容用一个展开的循环(而不是重复的交替)来描述,这样也更有效率:[^"\\]*(?:\\.[^"\\]*)*
显然,要处理没有平衡引号的字符串,可以使用所有格量词:[^"\\]*+(?:\\.[^"\\]*)*+或模仿它们的替代方法,以防止太多回溯。你也可以选择一个带引号的部分可以是一个开始引号,直到下一个(非转义)引号或字符串的结尾。在这种情况下,没有必要使用所有格量词,你只需要使最后一个引用是可选的。
注意:有时引号不是用反斜杠转义,而是通过重复引号转义。在这种情况下,内容子模式看起来像这样:[^"]*(?:""[^"]*)*
这些模式避免使用捕获组和反向引用(我的意思是(["']).....\1),并使用简单的替换,但在factor开头使用["']。
Perl像:
["'](?:(?<=")[^"\\]*(?s:\\.[^"\\]*)*"|(?<=')[^'\\]*(?s:\\.[^'\\]*)*')
(注意,(?s:…)是一个语法糖,用于在非捕获组中打开dotall/单线模式。如果不支持此语法,您可以轻松地为所有模式打开此模式或将点替换为[\s\ s])
(这种模式的编写方式完全是“手工驱动的”,没有考虑到最终的引擎内部优化)
ECMA脚本:
(?=["'])(?:"[^"\\]*(?:\\[\s\S][^"\\]*)*"|'[^'\\]*(?:\\[\s\S][^'\\]*)*')
POSIX扩展:
"[^"\\]*(\\(.|\n)[^"\\]*)*"|'[^'\\]*(\\(.|\n)[^'\\]*)*'
或者仅仅是:
"([^"\\]|\\.|\\\n)*"|'([^'\\]|\\.|\\\n)*'
模式(["'])(?:(?=(\\?))\2.)*?上面的\1完成了这项工作,但我担心它的性能(它不差,但可以更好)。我的比它快20%。
模式“(.*?)”是不完整的。我对阅读这篇文章的人的建议是不要使用它!!
例如,它不能捕获很多字符串(如果需要,我可以提供一个详尽的测试用例),如下所示:
$string = '你好吗?我很好,谢谢你;
其余的都和上面那个一样“好”。
如果你真的关心性能和精度,那么就从下面的开始:
/(['"])((\\\ 1 |。)* ?)\ 1 /通用
在我的测试中,它涵盖了我遇到的每一个字符串,但如果你发现一些不工作的东西,我很乐意为你更新它。
在在线正则表达式测试器中检查我的模式。