Парсинг текстового файла шаблоном столбца

Я задавался вопросом, существует ли простой способ использовать awk или какую-либо другую команду для парсинга текстового файла, таким образом что файл чего-то как:

Step Temp Enthalpy
0    0    -368
100  1    -369
200  2    -372
300  6    -362
400  9    -365
SHAKE stats (type/ave/delta) on step 500
1 1.09  8.71362e-08
500  13   -358
600  15   -339
.
.
900  25   -306
SHAKE stats (type/ave/delta) on step 1000
1 1.09 7.06858e-08
1000 28  -306
.
.
.

мог распечатать вывод только определенного столбца чисел, я хочу такой как только температурные значения. Я знаю, что мог просто сделать что-то как awk '{print $2}' поскольку температурные значения, но мой конкретный файл данных имеет другие строки различных данных прежде и после таблицы 'Step Temp Enthalpy', которая делает это непрактичным, таким образом, я хотел бы идеально отключить все прежде и после этой 'информации' Энтальпии Временного файла Шага и распечатал бы только конкретный столбец этого раздела файла данных, мне нужно. Файл данных также имеет ту 'строку' статистики ВСТРЯСКИ каждые 5 шагов в дополнение к строке после него '1 1.09.... и т.д.', который я хотел бы удаленный. Если бы я должен был распечатать только температурный столбец, то я хотел бы, чтобы он произвел:

0
1
2
6
9
13
15
.
.
25
28
2
задан 26 July 2018 в 06:39

2 ответа

Простой шаблон, который Вы имеете, должен вынуть столбец 2 в строках, содержащих/начинающих с цифрами. Обычная структура awk команды /Pattern in current line/ { commands};. Команды в фигурных скобках выполняются, только если шаблон найден в текущей строке. Поэтому мы можем сделать:

$ awk '/^[[:digit:]]/{print $2}' input.txt
0
1
2
6
9
1.09
13
15
25
1.09
28

Чтобы также удалить числа с плавающей точкой добавьте дополнительный шаблон с логической операцией И &&:

$ awk '/^[[:digit:]]/ && $0 !~ /[.]/ {print $2}' input.txt
0
1
2
6
9
13
15
25
28

С другой стороны, просто используйте шаблон отрицания для исключения статистики встряски:

awk '!/^SHAKE/ && $0 !~ /[.]/ {print $2}' input.txt 

Для рассматривания вопроса в комментарии можно объединить шаблон диапазона (что-то как /Pattern1/,/Pattern2/ {commands} ) с и если оператор. Шаблон диапазона выполнит команды в фигурных скобках только для строк, соответствующих диапазону, и затем если оператор может сделать дополнительную фильтрацию. В данном случае можно просто объединить его с предыдущим решением как так:

$ awk '$0 == "Step Temp Enthalpy",0 { if( $0 ~ /^[[:digit:]]/ && $0 !~ /[.]/  ) print $2  }' input.txt

Шаблон $0 == "Step Temp Enthalpy",0 показывает обработку точной строки Step Temp Enthalpy кому: 0, это - конец файла.

2
ответ дан 2 December 2019 в 02:12

Вот (возможно) более простой подход на основе структуры данных, а не при соответствии содержанию:

  • используйте арифметику по модулю, чтобы протестировать, являемся ли мы на одном из SHAKE stats строки
  • если так, хлебайте следующую строку с getline и движение
  • иначе распечатайте второе поле

Так

$ awk '!(NR%7) {getline; next} {print $2}' data
Temp
0
1
2
6
9
13
15


25
28
2
ответ дан 2 December 2019 в 02:12

Другие вопросы по тегам:

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