Страницы

Поиск по вопросам

четверг, 16 мая 2019 г.

Как сделать, чтобы моя функция set_checkpoints() корректно обрабатывала текстовый файл

У меня есть текстовый файл data.txt
яблоко банан абрикос яблоко апельсин апельсин мандарин абрикос абрикос абрикос абрикос абрикос
Я пытаюсь сделать так, чтобы после обработки файла data.txt функцией set_checkpoints() на выходе получался файл save.txt
//А//яблоко//А// //А//банан//А// //А//абрикос//А// //А//яблоко//А// //А//апельсин//А// //А//апельсин//А// //А//мандарин//А// //А//абрикос//А// //А//абрикос//А// //А//абрикос//А// //А//абрикос//А// //А//абрикос//А//
Но в результате у меня получается вот что:
//А//яблоко//А// //А//банан//А// //А//абрикос//А// яблоко //А//апельсин//А// апельсин //А//мандарин//А// абрикос абрикос абрикос абрикос абрикос
Решение: Нужно сделать так, чтобы функция при нахождении нужного слова из массива, продолжил поиск данного слова до конца файла, а не прерывался на первом же совпадении и переходил бы к следующему слову. В итоге у меня получается, что он находит из массива fruits совпадение со словом из текстового файла, отмечает его чекпойтами и переходит к поиску следующего слова из массива. Как сделать так, чтобы функция работала корректно?
Вот мой код:
import re
path = 'data.txt' # input data save = 'save.txt' # output data
def open_read(path): # функция открывает и считывает файл file = open(path, 'r') content = file.read() file.close() #print(content) return content
Fruits = ['яблоко','банан','абрикос','апельсин','мандарин'] # массив ключевых слов
n=len(Fruits) # определение размера массива Fruits
def set_checkpoints(content): # функция устанавливает checkpoints for i in range(n): find = re.compile(Fruits[i]) res = find.search(content) #lenght = len(find.findall(content)) # определяет общее количество конкретного найденного слова #print (lenght) #for i in range(lenght): if res == None: continue # Если не обнаружено слово else: k1 = res.start() k2 = res.end() content = content[:k1]+"//А//"+content[k1:k2]+"//А//"+content[k2:] print(content) return content ###############################################
content = open_read(path) # окрываем файл content = set_checkpoints(content) # обрабатываем файл функцией set_checkpoints()
file = open(save, 'w') # сохраняем файл file.write(content) file.close()
P.S. Я так понимаю тут дело заключается в методе search(), т.к. метод search() ищет по всей строке, но возвращает только первое найденное совпадение. Тут похоже нужно использовать метод findall(), т.к. этот метод возвращает список всех найденных совпадений. Но я не знаю, как в findall() реализовать установку чекпоинтов. Свойства start() и end() работают только в методе search().
Помогите, пожалуйста.


Ответ

Не нужны тут регулярные выражения:
fruits = ['яблоко', 'банан', 'абрикос', 'апельсин', 'мандарин']
with open('input.txt', encoding='utf-8') as f_in: with open('output.txt', 'w', encoding='utf-8') as f_out: for line in f_in: # Для удаления справа пустых символов: ' ', '
', '
', и т.п. line = line.rstrip()
# Если фрукт есть в списке if line in fruits: f_out.write('//А//{}//А//
'.format(line))

Если работать с текстом и через функцию:
FRUITS = ['яблоко', 'банан', 'абрикос', 'апельсин', 'мандарин']
def set_checkpoints(text: str) -> str: # В одну строку return '
'.join( '//А//{}//А//'.format(line) for line in text.splitlines() if line in FRUITS )
# NOTE: тот же код, что выше # new_lines = [] # # for line in text.splitlines(): # if line in FRUITS: # new_lines.append('//А//{}//А//'.format(line)) # # return '
'.join(new_lines)
with open('input.txt', encoding='utf-8') as f: content = f.read()
# Обрабатываем файл функцией set_checkpoints() content = set_checkpoints(content)
with open('output.txt', 'w', encoding='utf-8') as f: f.write(content)
Результат (output.txt):
//А//яблоко//А// //А//банан//А// //А//абрикос//А// //А//яблоко//А// //А//апельсин//А// //А//апельсин//А// //А//мандарин//А// //А//абрикос//А// //А//абрикос//А// //А//абрикос//А// //А//абрикос//А// //А//абрикос//А//

Комментариев нет:

Отправить комментарий