транспонировать переменное количество строк с переменным количеством столбцов в них до <pattern>, за которым следуют все строки до следующего <pattern> - PullRequest
0 голосов
/ 20 марта 2019

У меня есть следующий вход, относящийся к мультиинтерфейсной (десятки из них) части сетевого оборудования (обратите внимание, что строки с # предназначены только для пояснения и отсутствуют в данных):

eth<number1> 
# eth as pattern is fine, running number will be dealt with
parameter1 parameter2 parameter3...parameterN 
#ellipsis means and so on and is not literal
parameter21 parameter22
parameter31 parameter32 parameter33 parameter34
parameter41
eth<number2>
parameter1 parameter2
parameter21
.
.
.
.
parameterN1 parameterN2  
# again, vertical ellipsis is not literal and means simply that rows 
# with parameters can go on and on, it is not known in advance for 
# how long
eth<number3>
parameter1 parameter2
eth<number4>
parameter1 parameter2
parameter21

Желаемый результат должен выглядеть следующим образом:

eth<number1> parameter1 parameter2 parameterN parameter21 parameter22 parameter31 parameter32 parameter33 parameter34 parameter41 
# all in one line, with as many columns as there are parameters for 
# the given interface.
eth<number2> parameter1 parameter2....parameterNM
eth<number3> parameter1 parameter2
eth<number4> parameter1 parameter2 parameter21

Есть идеи, как этого добиться, предпочтительно, awk или sed?Любые уточняющие вопросы приветствуются, конечно.

Ответы [ 2 ]

2 голосов
/ 20 марта 2019

Это может сработать для вас (GNU sed):

sed -E '/^#/d;/^eth/!{H;$!d};x;s/\n/ /gp;x;h;d' file

Существует три сценария: строки, начинающиеся с #, строки, начинающиеся с `eth, и другие строки.

Если текущая строка является комментарием, удалите его.

Если текущая строка не начинается eth, добавьте ее в область удержания (HS) и удалите ее, если это не последняя строка.

В противном случае текущая строка начинается eth или является последней строкой, поэтому поменяйте местами на HS и, если в нем есть какие-либо переводы строк, замените их пробелами и напечатайте результат. Вернитесь к пространству шаблона и замените HS текущей строкой и удалите текущую строку, если только она не является последней строкой файла, в этом случае напечатайте ее.

0 голосов
/ 20 марта 2019

Это должно быть очень легко сделать в Perl.Строки eth легко сопоставить, и мы просто хотим объединить все строки между ними в одну строку.

#!/usr/bin/env perl
use strict;
use warnings;

my $collected;
while (my $line = <DATA>){
  next if $line =~ /^#/;
  if($line =~ /^eth/) {
    # new block of lines
    if ($collected) {
      print $collected, "\n";
      $collected = "";
    }
    chomp $line;
    $collected = $line;
  } else {
    # Append to collected lines
    chomp $line;
    $collected = "$collected $line";
  }
}
print $collected,"\n" if $collected;
__DATA__
eth<number1>
parameter1 parameter2 parameter3...parameterN
#ellipsis means and so on and is not literal
parameter21 parameter22
parameter31 parameter32 parameter33 parameter34
parameter41
eth<number2>
parameter1 parameter2
parameter21
parameterN1 parameterN2
eth<number3>
parameter1 parameter2
eth<number4>
parameter1 parameter2
parameter21

Это позволит проанализировать ваши образцы данных (игнорируя комментарии) и создать желаемыевыход.Конечно, это просто демо;Вы хотите open файл, в котором находятся данные, и прочитать его:

open my $fh, "<", "your.data" or die "Can't open file: $!\n";
...
while(my $line = <$fh>) { 
...
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...