Python 用正则表达式分割字符串
Python partition string with regular expressions
我正在尝试使用 Python 的分区和正则表达式来清理文本字符串。例如:
testString = 'Tre Bröders Väg 6 2tr'
sep = '[0-9]tr'
head,sep,tail = testString.partition(sep)
head
>>>'Tre Br\xc3\xb6ders V\xc3\xa4g 6 2tr'
头部仍然包含我要删除的 2tr。我不太擅长正则表达式,但 [0-9] 不应该吗?
我希望从这个例子中得到的输出是
head
>>> 'Tre Br\xc3\xb6ders V\xc3\xa4g 6
str.partition
不支持 regex ,因此当你给它一个像 - '[0-9]tr'
这样的字符串时,它试图在 testString
中找到确切的字符串以根据,它没有使用任何正则表达式。
根据documentation of str.partition
-
Split the string at the first occurrence of sep, and return a 3-tuple containing the part before the separator, the separator itself, and the part after the separator. If the separator is not found, return a 3-tuple containing the string itself, followed by two empty strings.
既然你说了,你只想要 head
,你可以使用 re.split()
method from re
模块,将 maxsplit 设置为 1
,然后取它的第一个元素,应该是等同于您尝试使用 str.partition
。示例 -
import re
testString = 'Tre Bröders Väg 6 2tr'
sep = '[0-9]tr'
head = re.split(sep,testString,1)[0]
演示 -
>>> import re
>>> testString = 'Tre Bröders Väg 6 2tr'
>>> sep = '[0-9]tr'
>>> head = re.split(sep,testString,1)[0]
>>> head
'Tre Bröders Väg 6 '
对于那些仍在寻找如何进行正则表达式分区的答案的人,请尝试以下功能:
import regex # re also works
def regex_partition(content, separator):
separator_match = regex.search(separator, content)
if not separator_match:
return content, '', ''
matched_separator = separator_match.group(0)
parts = regex.split(matched_separator, content, 1)
return parts[0], matched_separator, parts[1]
普通re.split()
方法
您可以使用re.split()
提取head
。
import re
testString = 'Tre Bröders Väg 6 2tr'
sep = r'[0-9]tr' # "r" is essential here!
head, tail = re.split(sep, testString)
head.strip()
>>>'Tre Bröders Väg 6'
巧克力洒re.split()
方法
如果你用()
捕获sep
,re.split()
的行为就像一个伪re.partition()
(Python中没有这样的方法,实际上.. .)
import re
testString = 'Tre Bröders Väg 6 2tr'
sep = r'([0-9]tr)' # "()" added.
# maxplit of 1 is added at the suggestion of Ángel ;)
head, sep, tail = re.split(sep, testString, 1)
head, sep, tail
>>>('Tre Bröders Väg 6 ', '2tr', '')
我来到这里是为了寻找一种使用基于正则表达式的方法 partition()
如 中所包含的那样,如果 re.split()
包含捕获组,则 re.split()
可以作为分隔符,因此基于正则表达式创建分区函数的最基本方法是:
re.split( "(%s)" % sep, testString, 1)
但是,这仅适用于简单的正则表达式。如果您按使用组的正则表达式拆分(即使不捕获),它也不会提供预期的结果。
我首先查看了 提供的函数,但它不必要地第二次运行正则表达式,更重要的是,如果模式与自身不匹配(它应该 string.split matched_separator,而不是 re.split)。
因此我实现了我自己的支持正则表达式的 partition() 版本:
def re_partition(pattern, string, return_match=False):
'''Function akin to partition() but supporting a regex
:param pattern: regex used to partition the content
:param content: string being partitioned
'''
match = re.search(pattern, string)
if not match:
return string, '', ''
return string[:match.start()], match if return_match else match.group(0), string[match.end():]
作为附加功能,它可以 return 匹配对象本身,而不仅仅是匹配的字符串。这允许您直接与分隔符的组进行交互。
并以迭代器形式:
def re_partition_iter(pattern, string, return_match=False):
'''Returns an iterator of re_partition() output'''
pos = 0
pattern = re.compile(pattern)
while True:
match = pattern.search(string, pos)
if not match:
if pos < len(string): # remove this line if you prefer to receive an empty string
yield string[pos:]
break
yield string[pos:match.start()]
yield match if return_match else match.group(0)
pos = match.end()
我正在尝试使用 Python 的分区和正则表达式来清理文本字符串。例如:
testString = 'Tre Bröders Väg 6 2tr'
sep = '[0-9]tr'
head,sep,tail = testString.partition(sep)
head
>>>'Tre Br\xc3\xb6ders V\xc3\xa4g 6 2tr'
头部仍然包含我要删除的 2tr。我不太擅长正则表达式,但 [0-9] 不应该吗?
我希望从这个例子中得到的输出是
head
>>> 'Tre Br\xc3\xb6ders V\xc3\xa4g 6
str.partition
不支持 regex ,因此当你给它一个像 - '[0-9]tr'
这样的字符串时,它试图在 testString
中找到确切的字符串以根据,它没有使用任何正则表达式。
根据documentation of str.partition
-
Split the string at the first occurrence of sep, and return a 3-tuple containing the part before the separator, the separator itself, and the part after the separator. If the separator is not found, return a 3-tuple containing the string itself, followed by two empty strings.
既然你说了,你只想要 head
,你可以使用 re.split()
method from re
模块,将 maxsplit 设置为 1
,然后取它的第一个元素,应该是等同于您尝试使用 str.partition
。示例 -
import re
testString = 'Tre Bröders Väg 6 2tr'
sep = '[0-9]tr'
head = re.split(sep,testString,1)[0]
演示 -
>>> import re
>>> testString = 'Tre Bröders Väg 6 2tr'
>>> sep = '[0-9]tr'
>>> head = re.split(sep,testString,1)[0]
>>> head
'Tre Bröders Väg 6 '
对于那些仍在寻找如何进行正则表达式分区的答案的人,请尝试以下功能:
import regex # re also works
def regex_partition(content, separator):
separator_match = regex.search(separator, content)
if not separator_match:
return content, '', ''
matched_separator = separator_match.group(0)
parts = regex.split(matched_separator, content, 1)
return parts[0], matched_separator, parts[1]
普通re.split()
方法
您可以使用re.split()
提取head
。
import re
testString = 'Tre Bröders Väg 6 2tr'
sep = r'[0-9]tr' # "r" is essential here!
head, tail = re.split(sep, testString)
head.strip()
>>>'Tre Bröders Väg 6'
巧克力洒re.split()
方法
如果你用()
捕获sep
,re.split()
的行为就像一个伪re.partition()
(Python中没有这样的方法,实际上.. .)
import re
testString = 'Tre Bröders Väg 6 2tr'
sep = r'([0-9]tr)' # "()" added.
# maxplit of 1 is added at the suggestion of Ángel ;)
head, sep, tail = re.split(sep, testString, 1)
head, sep, tail
>>>('Tre Bröders Väg 6 ', '2tr', '')
我来到这里是为了寻找一种使用基于正则表达式的方法 partition()
如 re.split()
包含捕获组,则 re.split()
可以作为分隔符,因此基于正则表达式创建分区函数的最基本方法是:
re.split( "(%s)" % sep, testString, 1)
但是,这仅适用于简单的正则表达式。如果您按使用组的正则表达式拆分(即使不捕获),它也不会提供预期的结果。
我首先查看了
因此我实现了我自己的支持正则表达式的 partition() 版本:
def re_partition(pattern, string, return_match=False):
'''Function akin to partition() but supporting a regex
:param pattern: regex used to partition the content
:param content: string being partitioned
'''
match = re.search(pattern, string)
if not match:
return string, '', ''
return string[:match.start()], match if return_match else match.group(0), string[match.end():]
作为附加功能,它可以 return 匹配对象本身,而不仅仅是匹配的字符串。这允许您直接与分隔符的组进行交互。
并以迭代器形式:
def re_partition_iter(pattern, string, return_match=False):
'''Returns an iterator of re_partition() output'''
pos = 0
pattern = re.compile(pattern)
while True:
match = pattern.search(string, pos)
if not match:
if pos < len(string): # remove this line if you prefer to receive an empty string
yield string[pos:]
break
yield string[pos:match.start()]
yield match if return_match else match.group(0)
pos = match.end()