BEGIN и END с помощью команды awk

Согласно руководству awk, BEGIN и END не используются для ввода ввода, а скорее предоставляют информацию о запуске и очистке скрипта awk. Вот пример:

ls -l | \ awk 'BEGIN { print "Files found:\n" } /\<[a|x].*\.conf$/ { print $9 }' Files found: amd.conf antivir.conf xcdroast.conf xinetd.conf 

Сначала это печатает строку для вывода. Затем он проверяет ввод для соответствия шаблону, где ввод начинается с a или x, за которым следует любой символ один или несколько раз, за ​​которым следует .conf. Для любых совпадений печатается 9-й столбец.

Тот факт, что мы вынуждены использовать здесь, означает, что awk может использовать только одну функцию печати, которая содержит BEGIN или END? Если нет, то почему мы не можем просто использовать функцию печати в начале без ключевого слова BEGIN? Кажется, BEGIN лишний.

  • Подсчет количества записей в столбце 2, где столбец 1 аналогичен
  • Замена строк с помощью словаря
  • команда | grep | awk | ... как выполнить
  • Удалите строку из определенного поля с помощью awk / sed
  • Как распечатать последнее слово, которое содержит разделитель поля
  • Как удалить повторяющиеся строки, сохраняя порядок и игнорируя регистр?
  • Я хочу найти строку и вытащить все строки между двумя шаблонами
  • Как обрабатывать ^ M в файлах csv с помощью sed & awk?
  • 4 Solutions collect form web for “BEGIN и END с помощью команды awk”

    BEGIN не лишний. Если вы не укажете BEGIN print будет выполнена для каждой строки ввода.

    Цитата из руководства :

    Правило BEGIN выполняется только один раз, прежде чем будет прочитана первая входная запись. Аналогично, правило END выполняется только один раз, после того, как все данные прочитаны.

     $ seq 5 | awk 'BEGIN{print "Hello"}/4/{print}' # Hello printed once Hello 4 $ seq 5 | awk '{print "Hello"}/4/{print}' # Hello printed for each line of input Hello Hello Hello Hello 4 Hello $ 

    awk обрабатывает каждую строку ввода для выражений, указанных в теле, отличных от блоков BEGIN и END . В случае блоков BEGIN и END awk будет обрабатывать операторы только один раз, прежде чем обработка ввода начнется и после обработки ввода будет выполнена соответственно. Без блока BEGIN не только вы не сможете печатать одноразовую информацию, такую ​​как заголовки, вы не сможете эффективно инициализировать некоторые из переменных, требуемых телом. Кроме того, FYI, awk программа может иметь несколько блоков BEGIN и END .

    awk выполняет каждый блок только тогда, когда шаблон перед ним совпадает. Пустой шаблон (только блок) соответствует каждой строке. BEGIN и END – это специальные шаблоны, соответствующие началу и концу файла (аналогично значению ^ и $ в горизонтальном направлении).

    Если вы хотите что-то выполнить перед чтением файла, используйте BEGIN . Например, инициализация счетчиков или что-то еще. Затем END может собрать результаты.

    В приведенном примере, который, я думаю, упрощен для педагогической ясности, вы правы, что это лишнее. Вы можете получить те же результаты без использования BEGIN .

     1 == NR { print "Files found:\n" } /\<[a|x].*\.conf$/ { print $9 } 

    будет давать те же результаты, поскольку оператор печати ограничивается только первой строкой ввода.

    При этом блоки BEGIN и END являются невероятно мощными инструментами. Как упоминалось в других решениях, вы можете использовать блок BEGIN для инициализации переменных или других подпрограмм, которые нужно выполнить только один раз, но также можно использовать для запуска команд Awk, когда нет файлов для обработки. Простой пример:

     BEGIN { print sqrt(12/4) } 

    Вы можете увидеть более серьезный пример программирования в Awk без обработки каких-либо входных данных здесь .

    Аналогично, блок END чрезвычайно полезен для выполнения вычислений и суммирования всех входных данных. Это невозможно сделать (обычно) без предварительного чтения во всех данных. Простой пример суммирующего ввода можно найти здесь

    Linux и Unix - лучшая ОС в мире.