2016-03-14 2 views
0

У меня есть список слов, которые я хочу перекрестно ссылаться на кучу текстов, и если в тексте присутствует слово из строки поиска, я хочу сохранить текст.Захват любого появления слова в тексте; RegEx; Python

search_string = ['Good', 'Bad', 'Ugly'] 

Мой код до сих пор:

retained_texts = [] 
for text in full_text: 
    if set(text) & search_string: 
     retained_texts.append(' '.join(text)) 

Здесь full_text список списков и text список слов.

Этот метод имеет очень низкий уровень точности, поскольку он сохраняет только тексты, в которых Good, Bad и Ugly являются отдельными словами. Однако он отвергает случаи, когда они внедряются другими словами.

Е.Г.,

Инстансы как Goodwill, Ugly-duckling, BadBoy, Good-Bad-Ugly и т.д. отвергнуты, в то время как я, безусловно, необходимо, чтобы они были сохранены.

Я бы предположил, что это можно решить с помощью регулярного выражения, но я, честно говоря, не знаю, как это сделать.

+0

бы 'Good' рассчитывать как в' товаров '? – zondo

+0

@zondo Да, было бы. Другими словами, любая строка, содержащая комбинацию символов из поиска, будет считаться. – Zlo

+0

Как насчет случая? «Хорошо» считается как «товар»? – zondo

ответ

2

Вы можете сделать это с помощью следующих регулярных выражений:

re.match('(Good|Bad|Ugly)', text) 

Таким образом, ваш полный код будет выглядеть примерно так:

import re 

search_string = ['Good', 'Bad', 'Ugly'] 
pattern = '({0})'.format('|'.join(map(re.escape, search_string))) 
retained_texts = [] 
for text in full_text: 
    if re.search(pattern, text): 
     retained_texts.append(' '.join(text)) 

UPDATE: В комментарии указывают есть проблема, если search_string содержит точки, скобки или любые другие символы, которые должны быть экранированы в регулярных выражениях. Это можно устранить, вызвав re.escape при построении шаблона, поэтому я соответствующим образом отредактировал приведенный выше пример.

+0

Полезно отметить, что это чувствительно к регистру, так что Good не подходит. Также возвращает None, если регулярное выражение не соответствует, но хорошо отвечает на вопрос. – Tom

+0

▲ для формирования изменения с использованием строковых методов. Мне понравился этот подход. Но вы должны отметить, что когда текст достаточно велик, и ваш список также значителен, это очень неэффективный подход. Проверяя этот [пример] (https://regex101.com/r/dN2wW9/1), вы поймете, почему я это сказал. Кроме того, когда список слов включает точку '.', ваша строка поиска будет формировать регулярное выражение, в котором оно будет ** metacharacher **, [example] (https://regex101.com/r/dN2wW9/2). –

+0

Это работает хорошо! Однако, если слово находится в круглых скобках - оно не возвращает объект. Например, 're.match (pattern, '(Bad)')' ничего не возвращает – Zlo

1

Вы также могли бы сделать это так:

search_list = ['Good', 'Bad', 'Ugly'] 
retained_texts = [] 
for text in full_text: 
    if any(search in word for word in text for search in search_list): 
     retained_texts.append(' '.join(text)) 
1

Вы можете придавить full_text первым, а затем сделать матч регулярного выражения:

>>> import re 
>>> search_string = ['Good', 'Bad', 'Ugly'] 
>>> full_text = [['yes','no'],['Bad','Ahh'],['Goodwill','Ugly-duckling','BadBoy','Good-Bad-Ugly']] 
>>> [j for j in [i for f in full_text for i in f] if re.findall('Good|Bad|Ugly',j)] 
['Bad', 'Goodwill', 'Ugly-duckling', 'BadBoy', 'Good-Bad-Ugly'] 
Смежные вопросы