对不匹配正则表达式模式的字符串的所有部分进行操作的函数
function to operate on all parts of string which don't match a regex pattern
假设我有一个字符串:
"a bb c exclude_start d 3 f g h _ k l . exclude_end n 0 P exclude_start q r exclude_end s"
然后说我要应用一个 upper
函数,它将 return:
"A BB C exclude_start d 3 f g h _ k l . exclude_end N 0 P exclude_start q r exclude_end S"
我想要一个允许 n
个排除块的解决方案,并将 upper
函数仅应用于这些块之外的字符。
如果有办法 regex
仅匹配 excludes
之外的字符串,然后仅将 upper
应用于这些字符串,那就太好了。
我不确定是否有办法用一个正则表达式来做到这一点,但这是我对此的思考过程。我想我们想把字符串分开,这样我们就可以只将不在排除块中的部分大写。这样做的方法是制作一个正则表达式来匹配排除块:
>>> import re
>>> exclude_pattern = re.compile(r'(exclude_start.*?exclude_end)')
我们需要在其中包含问号,这样它就不会贪婪地匹配。
由于我们希望保留与 exclude_pattern
匹配的字符串部分而不是将它们丢弃,我们可以使用 re.split
:
If capturing parentheses are used in pattern, then the text of all groups in the pattern are also returned as part of the resulting list.
这就是我们 exclude_pattern
.
中需要括号的原因
接下来我们要使用该模式拆分字符串:
>>> input_string = "a bb c exclude_start d 3 f g h _ k l . exclude_end n 0 P exclude_start q r exclude_end s"
>>> exclude_pattern.split(input_string)
['a bb c ', 'exclude_start d 3 f g h _ k l . exclude_end', ' n 0 P ', 'exclude_start q r exclude_end', ' s']
这给了我们所需的分离。
接下来我们要做的是 upper
仅 upper
与我们的排除模式不匹配的字符串。为此,我认为我们可以在我们的列表上映射一个 lambda,根据我们的排除模式检查每个条目,并且只有 upper
s 不匹配的条目:
>>> list(map(lambda s: s.upper() if not exclude_pattern.match(s) else s, exclude_pattern.split(input_string)))
['A BB C ', 'exclude_start d 3 f g h _ k l . exclude_end', ' N 0 P ', 'exclude_start q r exclude_end', ' S']
list()
只是为了让我们可以看到生成的地图对象中有什么。
之后我们将它们重新组合在一起:
>>> ''.join(map(lambda s: s.upper() if not exclude_pattern.match(s) else s, exclude_pattern.split(input_string)))
'A BB C exclude_start d 3 f g h _ k l . exclude_end N 0 P exclude_start q r exclude_end S'
如果你不想把它做成一行(有点恶心),我们可以把它做成一个函数:
def excluded_upper(input_string):
exclude_pattern = re.compile(r'(exclude_start.*?exclude_end)')
split_string = exclude_pattern.split(input_string)
output = []
for s in split_string:
if exclude_pattern.match(s):
output.append(s)
else:
output.append(s.upper())
return ''.join(output)
假设我有一个字符串:
"a bb c exclude_start d 3 f g h _ k l . exclude_end n 0 P exclude_start q r exclude_end s"
然后说我要应用一个 upper
函数,它将 return:
"A BB C exclude_start d 3 f g h _ k l . exclude_end N 0 P exclude_start q r exclude_end S"
我想要一个允许 n
个排除块的解决方案,并将 upper
函数仅应用于这些块之外的字符。
如果有办法 regex
仅匹配 excludes
之外的字符串,然后仅将 upper
应用于这些字符串,那就太好了。
我不确定是否有办法用一个正则表达式来做到这一点,但这是我对此的思考过程。我想我们想把字符串分开,这样我们就可以只将不在排除块中的部分大写。这样做的方法是制作一个正则表达式来匹配排除块:
>>> import re
>>> exclude_pattern = re.compile(r'(exclude_start.*?exclude_end)')
我们需要在其中包含问号,这样它就不会贪婪地匹配。
由于我们希望保留与 exclude_pattern
匹配的字符串部分而不是将它们丢弃,我们可以使用 re.split
:
If capturing parentheses are used in pattern, then the text of all groups in the pattern are also returned as part of the resulting list.
这就是我们 exclude_pattern
.
接下来我们要使用该模式拆分字符串:
>>> input_string = "a bb c exclude_start d 3 f g h _ k l . exclude_end n 0 P exclude_start q r exclude_end s"
>>> exclude_pattern.split(input_string)
['a bb c ', 'exclude_start d 3 f g h _ k l . exclude_end', ' n 0 P ', 'exclude_start q r exclude_end', ' s']
这给了我们所需的分离。
接下来我们要做的是 upper
仅 upper
与我们的排除模式不匹配的字符串。为此,我认为我们可以在我们的列表上映射一个 lambda,根据我们的排除模式检查每个条目,并且只有 upper
s 不匹配的条目:
>>> list(map(lambda s: s.upper() if not exclude_pattern.match(s) else s, exclude_pattern.split(input_string)))
['A BB C ', 'exclude_start d 3 f g h _ k l . exclude_end', ' N 0 P ', 'exclude_start q r exclude_end', ' S']
list()
只是为了让我们可以看到生成的地图对象中有什么。
之后我们将它们重新组合在一起:
>>> ''.join(map(lambda s: s.upper() if not exclude_pattern.match(s) else s, exclude_pattern.split(input_string)))
'A BB C exclude_start d 3 f g h _ k l . exclude_end N 0 P exclude_start q r exclude_end S'
如果你不想把它做成一行(有点恶心),我们可以把它做成一个函数:
def excluded_upper(input_string):
exclude_pattern = re.compile(r'(exclude_start.*?exclude_end)')
split_string = exclude_pattern.split(input_string)
output = []
for s in split_string:
if exclude_pattern.match(s):
output.append(s)
else:
output.append(s.upper())
return ''.join(output)