Как выполнить много строку grep

Я просто работал в к той же проблеме. Если это - та же проблема, у меня есть Вы, должен смочь решить его путем выбора пакета в синаптическом, то перейдите к Пакету> Версия Силы в меню и выберите новейшую версию.

15
01.10.2013, 00:51
8 ответов

Если данные всегда находятся в том формате, Вы могли бы просто записать это:

awk -vRS= '$4 == "free" {n+=$7}; END {print n}'

(RS= записи средств являются абзацами).

Или:

awk -vRS= '/state *= *free/ && match($0, "procs *=") {
  n += substr($0,RSTART+RLENGTH)}; END {print n}'
12
27.01.2020, 19:49
$ pbsnodes
node1
    state = free
    procs = 2
    bar = foobar

node2
    state = free
    procs = 4
    bar = foobar

node3
    state = busy
    procs = 8
    bar = foobar
$ pbsnodes | grep -A 1 free
    state = free
    procs = 2
--
    state = free
    procs = 4
$ pbsnodes | grep -A 1 free | grep procs | awk '{print $3}'
2
4
$ pbsnodes | grep -A 1 free | grep procs | awk '{print $3}' | paste -sd+ 
2+4
$ pbsnodes | grep -A 1 free | grep procs | awk '{print $3}' | paste -sd+ | bc 
6

https://en.wikipedia.org/wiki/Pipeline _ (Unix)

5
27.01.2020, 19:49

Вот один способ сделать это использование pcregrep.

$ pbsnodes | pcregrep -Mo 'state = free\n\s*procs = \K\d+'
2
4

Пример

$ pbsnodes | \
    pcregrep -Mo 'state = free\n\s*procs = \K\d+' | \
    awk '{ sum+=$1 }; END { print sum }'
6
4
27.01.2020, 19:49

Ваш выходной формат запущен для абзаца Perl, хлебайте:

pbsnodes|perl -n00le 'BEGIN{ $sum = 0 }
                 m{
                   state \s* = \s* free \s* \n 
                   procs \s* = \s* ([0-9]+)
                 }x 
                    and $sum += $1;
                 END{ print $sum }'

Примечание:

Это только работает, потому что идея Perl "абзаца" является блоком непустых строк, разделенных одной или несколькими пустыми строками. Если у Вас не было пустых строк между node разделы, это не работало бы.

См. также

3
27.01.2020, 19:49

Если у Вас есть данные фиксированной длины (фиксированная длина, относящаяся к количеству строк в записи), в sed можно использовать N управляйте (несколько раз), который соединяет следующую строку с пространством шаблона:

sed -n '/^node/{N;N;N;s/\n */;/g;p;}'

должен дать Вам вывод как:

node1;state = free;procs = 2;bar = foobar
node2;state = free;procs = 4;bar = foobar
node3;state = busy;procs = 8;bar = foobar

Для переменного рекордного состава (например, с пустой строкой разделителя), Вы могли использовать переходящие команды t и b, но awk вероятно, получит Вас там более удобным путем.

3
27.01.2020, 19:49

Реализация GNU grep идет с двумя аргументами, чтобы также распечатать строки прежде (-B) и после (-A) соответствие. Отрывок из страницы справочника:

   -A NUM, --after-context=NUM
          Print NUM lines of trailing context after matching lines.  Places a line containing  a  group  separator  (--)  between  contiguous  groups  of  matches.   With  the  -o  or
          --only-matching option, this has no effect and a warning is given.

   -B NUM, --before-context=NUM
          Print  NUM  lines  of  leading  context  before  matching  lines.   Places  a  line  containing  a group separator (--) between contiguous groups of matches.  With the -o or
          --only-matching option, this has no effect and a warning is given.

Таким образом в Вашем случае, Вы имели бы к grep для state = free и также распечатайте следующую строку. При объединении этого с отрывками от вопроса Вы прибудете во что-то как этот:

usr@srv % pbsnodes | grep -A 1 'state = free' | grep "procs = " | awk  '{ print $3 }' | awk '{ sum+=$1 } END { print sum }'
6

и немного короче:

usr@srv % pbsnodes | grep -A 1 'state = free' | awk '{ sum+=$3 } END { print sum }'
6
3
27.01.2020, 19:49
  • 1
    awk делает сопоставление с образцом; Вам не нужно grep: см. ответ Stephane –  jasonwryan 01.10.2013, 01:01
  • 2
    Ну, sed делает сопоставление с образцом также. Вы могли также использовать perl, или php, или что когда-либо язык Вы предпочитаете. Но по крайней мере заголовок вопроса, который задают для много строки grep... прекрасный ;-) –  binfalse 01.10.2013, 01:18
  • 3
    Да: но наблюдение Вас использовало awk так или иначе... :) –  jasonwryan 01.10.2013, 02:48

... и вот решение для Perl:

pbsnodes | perl -lne 'if (/^\S+/) { $node = $& } elsif ( /state = free/ ) { print $node }'
0
27.01.2020, 19:49

Можно использовать awk getline команда :

$ pbsnodes | awk 'BEGIN { freeprocs = 0 } \
                  $1=="state" && $3=="free" { getline; freeprocs+=$3 } \
                  END { print freeprocs }'

От man awk :

   getline               Set $0 from next input record; set NF, NR, FNR.

   getline <file         Set $0 from next record of file; set NF.

   getline var           Set var from next input record; set NR, FNR.

   getline var <file     Set var from next record of file.

   command | getline [var]
                         Run command piping the output either into $0 or var, as above.

   command |& getline [var]
                         Run  command  as a co-process piping the output either into $0 or var, as above.  Co-processes are a
                         gawk extension.
0
27.01.2020, 19:49

Теги

Похожие вопросы