命名正则表达式组“(?P <group_name> regexp)”:“ P”代表什么?


190

在Python中,该(?P<group_name>…) 语法允许人们通过其名称引用匹配的字符串:

>>> import re
>>> match = re.search('(?P<name>.*) (?P<phone>.*)', 'John 123456')
>>> match.group('name')
'John'

“ P”代表什么?我在官方文档中找不到任何提示。

我很想获得有关如何帮助我的学生记住该语法的想法。知道“ P”代表(或可能代表)什么会很有用。


16
P代表Placeholder
kev 2012年

1
@kev:似乎应该是一个答案?
ninjagecko 2012年

3
由于猜测是适当的,我猜想肯·汤普森是嬉皮士的同情者,“ P”代表“广atch香”。
aaronasterling'4

2
该问题已添加到“组”下的“堆栈溢出正则表达式常见问题解答”中。
aliteralmind 2014年

6
顺便说一句,如果你使用match.groups(带s),你会悄悄地得到一个元组的所有组-_- groups('name')=>('John', '123456')当你真正想要的是 group('name')=>'John' 我希望这可以节省的地方一定有人时间(s)。
szmoore

Answers:


276

既然我们都在猜测,我还是不妨告诉我:我一直认为它代表Python。这听起来可能很愚蠢-什么,P for Python?-但为了辩护,我隐约记得了这个主题[我的重点]:

主题:声明(?P ...)正则表达式语法扩展

来自:Guido van Rossum(gui ... @ CNRI.Reston.Va.US)

日期:1997年12月10日下午3:36:19

我对Perl开发人员(开发Perl语言的人)有不同寻常的要求。我希望这个(perl5-porters)是正确的列表。我正在抄送Python字符串信号,因为它是我在此讨论的大部分工作的起源。

您可能知道Python。我是Python的创造者;我计划在今年年底之前发布下一个“主要”版本Python 1.5。我希望Python和Perl可以在未来的几年中共存。异花授粉对两种语言都有好处。(我相信Larry在向Perl 5添加对象时对Python有很好的了解; O'Reilly出版了有关这两种语言的书籍。)

如您所知,Python 1.5添加了一个新的正则表达式模块,该模块与Perl的语法更加匹配。我们试图在Python的语法中尽可能地接近Perl语法。但是,正则表达式语法具有一些特定于Python的扩展名,它们都以(?P开头。目前有两个:

(?P<foo>...)与常规分组括号类似,但是在
执行匹配后,可以通过符号组名“ foo”访问该组所匹配的文本。

(?P=foo)匹配与名为“ foo”的组匹配的字符串。等效于\ 1,\ 2等,除了组是
通过名称而不是数字来引用的。

我希望这个特定于Python的扩展名不会与以后的Perl regex语法的任何Perl扩展名冲突。如果你有计划的使用(?P,请让我们尽快知道,以便我们能够解决冲突。 否则,这将是很好,如果(?P语法可以永久的Python特定的语法扩展保留。 (是有某种扩展注册表吗?)

拉里·沃尔(Larry Wall)回答:

[...]到目前为止,还没有注册表-您的请求是来自外部perl5-porter的第一个请求,因此这是一个相当低的带宽活动。(对不起,上周价格甚至更低-我去纽约的互联网世界。)

无论如何,就我而言,我的祝福一定会让你“ P”。(显然,Perl在这一点上不需要'P'。:-) [...]

所以我不知道P最初的选择是由-模式引起的吗?占位符?企鹅?-但您可以理解为什么我总是将其与Python关联。考虑到(1)我不喜欢正则表达式并且尽可能避免使用它们,以及(2)这个线程发生在15年前,这有点奇怪。


5
也许是“特定于Python的扩展”?
jmort253

53
哇,您确实在这里找到了一些很好且相关的历史数据!我对Guido的帖子的解释是,“ P”代表“ Python特定的扩展”。
Eric O Lebigot 2012年

1
是的,这对我来说是确定的。因此具有讽刺意味的是,Perl和PCRE最初复制了语法,只是因为Python是第一种支持命名捕获的方式。但是他们也支持(?<group_name>…)语法,这似乎是最流行的-即使Java现在也支持它。
艾伦·摩尔

3
+1这是最好的尴尬答案之一,防御起来很不错:)。起初,我认为这太愚蠢了。但最后,我完全同意。
Sumudu

4
我喜欢在参与Perl时,甚至Python的创建者也使用奇怪的奥术语法,并且Perl社区对此完全满意。如果您尝试将Perl特定的扩展/语法添加到Python,那么到处都是鲜血。
基思·里普利

20

模式!该组命名一个(子)模式,供以后在正则表达式中使用。有关如何使用此类组的详细信息,请参见此处的文档


3
+1:这是一个很好的助记符设备:(?P<name>…)是“ pattern name”。但是,在正则表达式中,一切都是模式,因此仅将(?P<…>…)组标记为模式有点奇怪。但是,这将对我的学生有用。:)
Eric O Lebigot 2012年

2
@EOL不会教学生虚假的事情。当您达到精确度时,很难比他们想像的要强。例如。对我来说,有些需要多年的倍数5。矛盾的是,鼓励人们随便说话,只是总是非常清楚明确。完整地告诉学生您以前的评论(修订最后一句话;)。)
n611x007 2013年

7

Python扩展。从Python Docos:

Perl开发人员选择的解决方案是使用(?...)作为扩展语法。?括号后立即是语法错误,因为?无需重复,因此不会带来任何兼容性问题。?之后的字符 指示正在使用什么扩展名,因此(?= foo)是一回事(正向超前断言),而(?:foo)是另外一回事(包含子表达式foo的非捕获组)。

Python支持Perl的几种扩展,并在Perl的扩展语法中添加了扩展语法。如果问号后的第一个字符是P,则说明它是特定于Python的扩展名

https://docs.python.org/3/howto/regex.html


发现得好!这证实了帝斯曼的感觉。
Eric O Lebigot
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.