Перенаправление вывода print в несколько файлов в awk

Перенаправление вывода print в несколько файлов в awk

Я хочу напечатать одни и те же строки в 2 разных файла. Что я делаю сейчас:

print ID[i]" "Value[i]" "TS1[i]" "TS2[i] > "file1.txt";
print ID[i]" "Value[i]" "TS1[i]" "TS2[i] > "file2.txt";

Могу ли я написать одну команду для перенаправления в два разных файла?

РЕДАКТИРОВАТЬ

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

решение1

С . этого сделать нельзя awk.

Используя tee, вы можете сделать что-то вроде этого:

$ awk '{print ID[i]" "Value[i]" "TS1[i]" "TS2[i]}' file | tee out1 out2

Используется tee -a, если вы хотите добавить, а не перезаписать существующие файлы.

Если вы не хотите печатать весь вывод, попробуйте:

awk '
    BEGIN {outfile["a.txt"];outfile["b.txt"]}
    { for (file in outfile) { print > file } }' file

решение2

В awk, вместо перенаправления на файл с помощью print "text" > "file", вы можете перенаправить на команду, используя:

print "something" | "tee file1.txt file2.txt"

В первый раз, когда вы используете это |, awkпорождает команду, а в следующий раз она повторно использует ту же команду, так что она не начинает новую teeкаждый раз, когда вы это делаете, и не перезаписывает файлы (вам нужно вызвать , close("tee file1.txt file2.txt")если вы действительно хотите awkначать новую команду в следующий раз). Однако, если вы сделаете и то, > "file1.txt"и другое, | "tee file1.txt..."возникнет конфликт.

Тогда вы можете вместо этого использовать >> "file1.txt"и | "tee -a file1.txt...".

Однако я бы все равно выбралforПодход @cuonglmили используйте awkфункцию, так как это будет чище и эффективнее.

решение3

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

function print_to_files( message, file_a, file_b ) {
   print message > file_a;
   print message > file_b;
}

message = sprintf( "%s %s %s %s", ID[i], Value[i], TS1[i], TS2[i] )
print_to_files( message , "filea", "fileb" );'

Или жестко закодируйте файлы, если это все, что вам нужно.

function print_to_files( message ) {
   print message > "/path/to/filea";
   print message > "/path/to/fileb";
}

message = sprintf( "%s %s %s %s", ID[i], Value[i], TS1[i], TS2[i] )
print_to_files( message );'

решение4

Вы можете сделать это с sed- но без более четкого представления о вашем вкладе я не знаю, как это конкретно продемонстрировать. Тем не менее, вот общий пример:

seq 10 | sed -ne '/1/w ./onesfile.txt' -e '/3/w threesfile.txt'

Это записывает только строки, содержащие a 1в onesfile.txtи в противном случае for 3- все остальное удаляется. ЭтооченьБазовый пример того, как это может работать, но если бы вы могли предоставить образец входных данных, я мог бы сделать немного лучше.

После sedоткрытия файла для записи он остается открытым до тех пор, пока процесс не будет завершен. Он не обрезает постоянно свои записи. Дескрипторы файлов сохраняются на протяжении всего срока действия процесса.

Связанный контент