首页 > 解决方案 > Python 正则表达式在单词周围取字符

问题描述

我想在我的正则表达式查询中匹配特定单词之前和之后包含 5 个字符。这些词在一个列表中,我对其进行了迭代。

请参阅下面的示例,这是我尝试过的:

import re

text = "This is an example of quality and this is true."

words = ['example', 'quality']

words_around = []

for word in words:
    neighbors = re.findall(fr'(.{0,5}{word}.{0,5})', str(text))
    words_around.append(neighbors)

print(words_around)

输出为空。我希望一个数组包含['s an exmaple of q', 'e of quality and ']

标签: pythonregexpandas

解决方案


您可以在此处使用 PyPi 正则表达式,它允许无限长的后向模式:

import regex
import pandas as pd

words = ['example', 'quality']

df = pd.DataFrame({'col':[
    "This is an example of quality and this is true.",
    "No matches."
    ]})

rx = regex.compile(fr'(?<=(.{{0,5}}))({"|".join(words)})(?=(.{{0,5}}))')

def extract_regex(s):
    return ["".join(x) for x in rx.findall(s)]
    
df['col2'] = df['col'].apply(extract_regex)

输出:

>>> df
                                               col                                    col2
0  This is an example of quality and this is true.  [s an example of q, e of quality and ]
1                                      No matches.                                      []

模式及其使用方式都很重要。

fr'(?<=(.{{0,5}}))({"|".join(words)})(?=(.{{0,5}}))'部分定义了正则表达式模式。这是一个“原始”的 f 字符串文字,f可以在字符串文字中使用变量,但它还需要将其中的所有文字大括号加倍。给定当前words列表的模式看起来像(?<=(.{0,5}))(example|quality)(?=(.{0,5})),请参阅其在线演示。它在words内部正向后视之前捕获 0-5 个字符,然后捕获words,然后在正向前瞻中捕获接下来的 0-5 个字符(环视用于确保找到任何重叠匹配)。

["".join(x) for x in rx.findall(s)]部分将每个匹配项的组连接成一个字符串,并返回一个匹配项列表作为结果。


推荐阅读