【问题标题】:Split string with regex not working使用正则表达式拆分字符串不起作用
【发布时间】:2014-05-14 11:59:42
【问题描述】:

我正在尝试使用一些正则表达式拆分大文件。问题是我想在拆分后在文本中保留分隔符,并且我尝试在正则表达式的开头添加 ?= ,但是它没有拆分。我在 Sublime 中尝试了修改的正则表达式,它在那里工作。

文字是这样的:

2014 年 8 月 7 日 01:01:01 PM
一些文字
2014 年 8 月 7 日 02:02:02 PM


所以,日期,然后是一些文本和日期。我想用识别该日期的正则表达式分割文本。

第一个版本的正则表达式,非常适合我的目的:

\w{3}\s\d{2}\,\s\d{4}\s\d{1,2}\:\d{2}\:\d{2}\s[AM|PM].)

Python 中的代码是这样的:

allparts = re.compile(r'\w{3}\s\d{2}\,\s\d{4}\s\d{1,2}\:\d{2}\:\d{2}\s[AM|PM].').split(alltext)

添加 ?= 后是这样的:

allparts2 =re.compile(r'(?=\w{3}\s\d{2}\,\s\d{4}\s\d{1,2}\:\d{2}\:\d{2}\s[AM|PM].)').split(alltext)

我在第二个代码中做错了什么?

【问题讨论】:

  • 怎么样:(?=\w{3} \d{2}, \d{4}, [\d:]+ (?=AM|PM))
  • 我找不到任何东西。
  • 你的 allparts / allparts 在每种情况下返回什么?

标签: regex python-3.x


【解决方案1】:

对不起,我的第一个答案是错误的:)尽量不要添加?=,只把它放在括号中:

allparts2 =re.compile(r'(\w{3}\s\d{2},\s\d{4}\s\d{1,2}\:\d{2}\:\d{2}\s[AM|PM].)').split(alltext)

那就不编译试试吧……

allparts2 = re.split('(\w{3}\s\d{2},\s\d{4}\s\d{1,2}\:\d{2}\:\d{2}\s[AM|PM].)', alltext)

使用时:

#!/usr/local/bin/python2.7
import re

alltext = "Aug 07, 2014 01:01:01 PM some text Aug 07, 2014 02:02:02 PM another text Aug 07, 2014 03:03:03 AM " 

allparts2 = re.split('(?=\w{3}\s\d{2},\s\d{4}\s\d{1,2}\:\d{2}\:\d{2}\s[AM|PM].)', alltext)
print(allparts2)

结果是:

Executing the program....
$python2.7 main.py
['Aug 07, 2014 01:01:01 PM some text Aug 07, 2014 02:02:02 PM another text Aug 07, 2014 03:03:03 AM ']

使用时:

#!/usr/local/bin/python2.7
import re

alltext = "Aug 07, 2014 01:01:01 PM some text Aug 07, 2014 02:02:02 PM another text Aug 07, 2014 03:03:03 AM "


allparts2 = re.split('(?:\w{3}\s\d{2},\s\d{4}\s\d{1,2}\:\d{2}\:\d{2}\s[AM|PM].)', alltext)

print(allparts2)

结果是:

Executing the program....
$python2.7 main.py
['', ' some text ', ' another text ', ' ']

使用时:

#!/usr/local/bin/python2.7
import re

alltext = "Aug 07, 2014 01:01:01 PM some text Aug 07, 2014 02:02:02 PM another text Aug 07, 2014 03:03:03 AM "


allparts2 = re.split('(\w{3}\s\d{2},\s\d{4}\s\d{1,2}\:\d{2}\:\d{2}\s[AM|PM].)', alltext)

print(allparts2)

结果是:

Executing the program....
$python2.7 main.py
['', 'Aug 07, 2014 01:01:01 PM', ' some text ', 'Aug 07, 2014 02:02:02 PM', ' another text ', 'Aug 07, 2014 03:03:03 AM', ' ']

只是为了比较不同的形式。

【讨论】:

  • 我不知道问题出在哪里。我单独尝试了您的代码,它工作正常。但是当我在我的脚本中复制正则表达式时,它在那里不起作用。可能是因为我的字符串是文件中的数据吗?我打开了文件,并从 read() 方法中保存了所有内容。
  • 如果您打印出包含文件中数据的字符串,以查看其中的确切内容,也会有所帮助。
  • 只是 data = openFile.read()。但是我没有这个就解决了我的问题,只是简单地编写了我自己的拆分方法。但是您的方法适用于另一个文件,因此我将在那里使用该正则表达式。 Tnx。
【解决方案2】:

虽然我不熟悉 Python 风格,但Pythex 给了我以下我认为正确的结果:

result

即使这些不是,据我所知,您的正则表达式中有几件事是不必要和/或不正确的。

  • 逗号不需要转义
  • 条件不是由 [ condo | cond2] ,而是用括号 (cond1|cond2)
  • 您拥有的\s 是可选的,因为正则表达式会捕获一个空格,如果您想捕获一个空格,这是正确的,例如空格字符、制表符、回车符、..

最后,您添加的项目 ?= 是一个前瞻,?: 使其匹配,但不使其成为您的捕获组的一部分。

试试这个正则表达式:(?:\w{3} \d{2}, \d{4}, [\d:]+ (?:AM|PM))

【讨论】:

  • 没什么。尽管如此,拆分后分隔符仍然丢失。
【解决方案3】:

python 的 re.split() 似乎不会在零长度匹配上进行拆分。

但是,手册说

如果在模式中使用捕获括号,则模式中所有组的文本也会作为结果列表的一部分返回。

...

如果分隔符中有捕获组并且匹配到字符串的开头,则结果将以空字符串开头。

所以你可以使用:

allparts2 = re.compile(r'(\w{3}\s\d{2}\,\s\d{4}\s\d{1,2}\:\d{2}\:\d{2}\s(?:AM|PM))')

匹配的表达式被一个捕获组包围(还要注意最后的非捕获组)。结果是:

['', 'Aug 07, 2014 01:01:01 PM', ' some text ', 'Aug 07, 2014 02:02:02 PM', ' another text ', 'Aug 07, 2014 03:03:03 AM', ' ']

然后您可以通过对allparts[1], allparts[2] 等(2n+1、2n+2)进行分组来创建文件。

【讨论】:

  • 对不起,我在一年后错误地添加了','。它应该没有','
  • 而且,这仍然会找到所有行,但在拆分时,它会删除它们。
  • 这是另一个镜头。我删除了更正,因为它只是一个错字。我仍然留下了更正的替换并删除了最后一个.
猜你喜欢
  • 2017-02-23
相关资源
最近更新 更多