У меня есть этот файл 1.txt
:
-e a
b
-e c
d
-e e
f
Я хочу разбить его на следующие два files.
2.txt
-e a
-e c
-e e
3.txt
b
d
f
где 2.txt
содержит все строки, начинающиеся с -e
и 3.txt
содержит все остальные строки. Дополнительные новые строки (такие как дополнительная новая строка в середине оригинала) могут быть проигнорированы или сохранены, и порядок не имеет значения.
Я пытался использовать split
, но это не выглядит таким образом, я могу использовать шаблон для разделения (вместо фиксированного числа строк в файле разделения).
Использование grep
:
grep -E '^-e' 1.txt >2.txt
grep -E '[^-]' 1.txt >3.txt
Я не знаю, как это сделать путем установки непосредственно на ОС. Другой подход может заключаться в использовании docker для запуска отдельных контейнеров.
Понимание того, зачем вам нужна такая настройка, может помочь мне дать вам более подробный ответ.
В качестве отправной точки я рекомендую заглянуть в докер DevilBox.
sed -n '/^-/p' 1.txt > 2.txt
sed -n -r '/^(-|[[:space:]]*$)/!p' 1.txt > 3.txt
Вот тест производительности:
$ cat 1.txt | wc -l | sed -r -e 's/([0-9]{6}$)/ \1/' -e 's/([0-9]{3}$)/ \1 lines/'
1 144 270 lines
$ TIMEFORMAT=%R
$ time sed -e '/^-/!d' -e '/^[[:space:]]*$/d' 1.txt > 2.txt
0.357
$ time sed -e '/^-/d' -e '/^[[:space:]]*$/d' 1.txt > 3.txt
0.323
$ time sed -n '/^-/p' 1.txt > 2.txt
0.221
$ time sed -n -r '/^(-|[[:space:]]*$)/!p' 1.txt > 3.txt
0.402
Вот решение awk
:
awk '{ if ( /^-/ ) print > "2.txt"; else if ( NF ) print > "3.txt" }' 1.txt
Тест производительности:
$ cat 1.txt | wc -l | sed -r -e 's/([0-9]{6}$)/ \1/' -e 's/([0-9]{3}$)/ \1 lines/'
1 144 270 lines
$ TIMEFORMAT=%R
$ time awk '{ if ( /^-/ ) print > "2.txt"; else if ( NF ) print > "3.txt" }' 1.txt
0.372
Сохранение пустых строк:
$ sed -n -e '/^-e/{w 2.txt' -e 'd}' -e 'w 3.txt' 1.txt
, давая
$ head {1,2,3}.txt
==> 1.txt <==
-e a
b
-e c
d
-e e
f
==> 2.txt <==
-e a
-e c
-e e
==> 3.txt <==
b
d
f
Если вы предпочитаете пропускать пустые строки, добавьте регулярное выражение «любой символ» к последней записи:
sed -n -e '/^-e/{w 2.txt' -e 'd}' -e '/./w 3.txt' 1.txt