Добавить первую строку абзаца в несколько строк - PullRequest
1 голос
/ 05 ноября 2011

У меня есть файл с разделителями табуляции, который содержит дату, строку заголовка, некоторые значения, пустую строку, а затем он повторяется снова и снова несколько раз.Файл выглядит примерно так:

November 3, 2011
column_name1    column_name2    column_name3    column_name4
value   value   value   value
value   value   value   value
value   value   value   value
value   value   value   value

November 4, 2011
column_name1    column_name2    column_name3    column_name4
value   value   value   value
value   value   value   value
value   value   value   value
value   value   value   value

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

date    column_name1    column_name2    column_name3    column_name4
November 3, 2011    value   value   value   value
November 3, 2011    value   value   value   value
November 3, 2011    value   value   value   value
November 3, 2011    value   value   value   value

date    column_name1    column_name2    column_name3    column_name4
November 4, 2011    value   value   value   value
November 4, 2011    value   value   value   value
November 4, 2011    value   value   value   value
November 4, 2011    value   value   value   value

Ответы [ 3 ]

3 голосов
/ 05 ноября 2011

Использование 'Sed'

Содержимое 'infile':

$ cat infile
November 3, 2011
column_name1    column_name2    column_name3    column_name4
value   value   value   value
value   value   value   value
value   value   value   value
value   value   value   value

November 4, 2011
column_name1    column_name2    column_name3    column_name4
value   value   value   value
value   value   value   value
value   value   value   value
value   value   value   value

Содержимое сценария sed:

$ cat script.sed
## When line has a date.
/[0-9]\+,[ ]*[0-9]\{4\}/ {
        ## Save date to HS (hold space).
        h
        ## Read next line (header).
        N
        ## Insert 'date' string at the beginning of the line.
        s/.*\n/date\t/
        ## Print and read next line.
        P
        n
}

## Process next line if blank line found.
/^[ \t]*$/ {
        p
        d
}

## Process data inserting the date in the beginning.
## Put at the end of PS (pattern space) the date saved before and exchange it 
## with the rest of the line. Print after that.
G
s/^\(.*\)\n\(.*\)$/\2\t\1/
p

Выполнение сценария:

$ sed -n -f script.sed infile
date    column_name1    column_name2    column_name3    column_name4
November 3, 2011        value   value   value   value
November 3, 2011        value   value   value   value
November 3, 2011        value   value   value   value
November 3, 2011        value   value   value   value

date    column_name1    column_name2    column_name3    column_name4
November 4, 2011        value   value   value   value
November 4, 2011        value   value   value   value
November 4, 2011        value   value   value   value
November 4, 2011        value   value   value   value
2 голосов
/ 05 ноября 2011

Это решение GNU sed может работать:

 sed -r '/^[A-Z][a-z]+\s+[0-9][0-9]?,\s+([0-9]{4})/,/^$/{//{h;/^$/!{s/.*//;N;s/\n/date /;b}}};G;s/(.*)\n(.*)/\2 \1/;' input_file

РЕДАКТИРОВАТЬ: я должен был включить объяснение!

Команда sed изменяет только строки между теми, которые начинаются с даты /^[A-Z][a-z]+\s+[0-9][0-9]?,\s+([0-9]{4})/и пустая строка /^$/. Если это так, и строка соответствует одному из этих двух условий //, она сохраняет ее в пространстве удержания h, дополнительно, если строка не является пустой (т.е. это дата), он очищает его s/.*//, добавляет следующую строку N и затем добавляет к нему литерал date s/\n/data.Когда все это сделано, он прерывает b для чтения в следующей строке.Для всех следующих строк (помните, что это в начальном условии), он добавляет пробел удержания G (строка, содержащая дату) к текущей строке, затем с помощью подстановки добавляет дату к дате и теряет символ новой строки s/(.*)\n(.*)/\2 \1/ (побочный эффект).команды G).Вуаля!

2 голосов
/ 05 ноября 2011

Awk.

BEGIN {
    FS = "\n"
    RS = "\n\n"
    OFS = "\t"
    #ORS = "\n"
}
{
    print "date" OFS $2
    for (i = 3; i <= NF; i++)
        print $1 OFS $i
    print ""
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...