在pandas的“str.extract()”中使用正则表达式的“意外”行为

时间:2017-06-30 18:10:42

标签: python regex pandas

我正在尝试掌握正则表达式,并且我遇到了str.extract方法中包含的那个:

movies['year']=movies['title'].str.extract('.*\((.*)\).*',expand=True)

应该检测并提取括号中的任何一个。因此,如果给定此字符串:foobar (1995),则应返回1995。但是,如果我打开终端并输入以下内容

echo 'foobar (1995)` | grep '.*\((.*)\).*'

匹配整个字符串,而不仅仅是括号之间的内容。我假设该方法使用BRE风格,因为括号scaping,grep(默认行为)也是如此。此外,regex匹配整个字符串的蓝色和年份的绿色(捕获组)。我在这里错过了什么吗?正则表达式在python中完美运行

2 个答案:

答案 0 :(得分:2)

首先,Pandas .str.extract()的行为是非常期待的:它只返回捕获组内容。与extract一起使用的模式至少需要1个捕获组:

  

pat : string
  带捕获组的正则表达式模式

如果使用命名捕获组,则新列将以命名组命名。

您提供的grep命令可以缩减为

grep '\((.*)\)'

因为grep能够匹配行部分(不需要完整的行匹配)并且每行工作:一旦找到匹配,则返回整行。要覆盖该行为,您可以使用-o开关。

使用grep,您无法返回捕获组内容。这可以通过使用-P选项的PCRE regexp解决,但是在Mac上不可用,例如。 sedawk也可以在这些情况下提供帮助。

答案 1 :(得分:1)

尝试使用:

movies['year']= movies['title'].str.extract('.*\((\d{4})\).*',expand=False)

  • 如果您希望它返回DataFrame或应用多个捕获组,请设置 expand = True
  • 一年总是由4位数组成。所以正则表达式: \((\ d {4})\)匹配括号之间的任何日期。