Как извлечь значения из текста, используя несколько (вложенных) разделителей - PullRequest
2 голосов
/ 15 марта 2011

Изо дня в день мне нужно извлечь куски текста из журналов и других текстовых данных в различных смешанных форматах. Есть ли утилита (например, awk, grep и т. Д.), Которую я мог бы использовать, чтобы быстро выполнить задачу, не прибегая к написанию длинных скриптов bash / perl / python?

Пример 1: Для ввода текста ниже

mylog user=UserName;password=Password;other=information

Я хотел бы извлечь значения имени пользователя и пароля. Псевдо-утилита будет выглядеть примерно так ( a la awk):

cat input-text.txt | magic --delimit-by=";" --then-by="="
  '{print "The username is $values[0][1] and password is $values[1][1]"}'

Где входная строка, разделенная ;, помещена в массив $values, а каждое значение в этом массиве дополнительно разделено = для формирования вложенного массива.

Еще лучше, было бы неплохо иметь что-то вроде этого:

cat input-text.txt | magic --map-entry-sep=";" --map-key-val-sep="="
  '{print "The username is $[user] and password is $[password]"}'

Где результат анализа преобразуется в карту для удобного поиска по ключу.

Пример 2: Было бы неплохо проанализировать и тройные вложенные элементы. Рассмотрим вводимый текст как

mylog mylist=one,two,three;other=information

Я бы хотел извлечь 2-й элемент списка mylist, используя что-то вроде:

cat input-text.txt | magic --delimit-by=";" --then-by="=" --and-then-by=","
  '{print "The second element of mylist is: $values[0][1][1]}'

Конечно, я бы предпочел использовать какой-то синтаксический анализатор JSON и преобразовать входные данные в соответствующий формат объекта / карты / списка для упрощения извлечения, но это невозможно, поскольку я работаю с данными в разных форматах.

Я обычно использую комбинацию awk, grep, cut и sed, объединенную с использованием нескольких каналов, и извлекаю каждое интересующее значение (столбец) за раз, но это утомительно и требует объединения различных столбцов в один позже. Обычно мне нужны все извлеченные столбцы в формате CSV для дальнейшей обработки в Excel.

Буду признателен за любые предложения или комментарии.

1 Ответ

3 голосов
/ 15 марта 2011
$ echo 'mylog user=UserName;password=Password;other=information' | 
    awk -F '[ ;]' -v keysep="=" \
        '{
              for (i=1; i<=NF; i++) {
                  split($i, t, keysep); 
                  a[t[1]] = t[2]
              };
         print "The username is " a["user"] " and password is " a["password"]
         }'
The username is UserName and password is Password

$ echo 'mylog mylist=one,two,three;other=information' | awk -F "[ =,;]" '{print $4}'
two
...