Как новичок, я пытаюсь решить следующую проблему (сценарий bash или python):
файл (~ 50G!):
marker
xxx
xxx
xxx
pattern
marker
xxx
xxx
xxx
marker
xxx
xxx
xxx
pattern
Я хотел бы найти способ удалить линии между двумя markers
+ первым marker
, но не последним вхождением marker
если ни один pattern
может быть найден по всем линиям.
Требуемый результат:
marker
xxx
xxx
xxx
pattern
[empty!]
marker
xxx
xxx
xxx
pattern
Я попытался решить его с помощью регулярного выражения или awk (это очень застенчивое начало)
awk '/marker/{f=1} f; /marker/{f=1}' file
но мне трудно понять, как реализовать это в функции, которая решила бы всю проблему. Это сделало бы меня очень счастливым, если бы кто-то мог мне помочь!
ура
Вот способ сделать это в python. Обработайте marker
как разделитель, затем удалите что-либо из фрагментов текста между ними, которые не содержат pattern
f = open('markerfile.txt','r')
lines = f.read().split('marker\n')
lines = [entry for entry in lines if 'pattern' in entry or not entry]
print 'marker\n'.join(lines)
Редактировать: бит бит or not entry
в понимании списка просто обрабатывает случай, когда marker
является первой строкой в файле.
Редактировать 2: Здесь потоковая версия (лучше подходит для больших файлов.) Она использует islice
из itertools
для получения n
строк файла за раз. Остальная часть алгоритма более или менее одинакова.
from itertools import islice
f = open('markerfile.txt','r')
fout = open('markersout.txt','w')
n=5
while True:
next_n_lines = ''.join(list(islice(f, n)))
if not next_n_lines:
break
lines = next_n_lines.split('marker\n')
lines = [entry for entry in lines if 'pattern' in entry or not entry]
print >> fout, 'marker\n'.join(lines).strip()
f.close()
fout.close()