Как мне вернуться из сценария awk обратно в командную строку?

494
dacfer

У меня есть простой сценарий awk test1.awk:

{ x=temp; print x; } 

Когда я запускаю его из командной строки с:

awk -v temp=hello -f test1.awk 

Я получаю только курсор. Я нажимаю Enter, он пишет «привет» и дает другой курсор, Enterснова нажимает и снова пишет «привет» и т. Д. Просто идет в бесконечном цикле, требующем ввода от пользователя, и никогда не возвращается в командную строку.

D:\>awk -v temp=hello -f test1.awk  hello  hello  hello  hello ^C D:\> 

Как мне заставить его написать «привет» (не требуя ввода данных пользователем) и затем остановиться?

0
Ваш пример одновременно сложен и тривиален. Он сложен в том смысле, что в нем есть переменная, которая должна быть установлена ​​с помощью `-v`, иначе программа ничего не сделает, а затем копирует эту переменную в другую переменную без реальной функциональной цели. Это тривиально в том смысле, что он ничего не делает, кроме как печатает значение этой переменной. Когда вы отлаживаете / устраняете неполадки, тривиально это хорошо, а сложно плохо. Чтобы заставить * что-то * (что-либо) работать, вы, вероятно, должны начать с тривиальных вещей, таких как ` `. Для чуть менее тривиального примера, см. Мой ответ. Scott 6 лет назад 0

3 ответа на вопрос

1
Lewis M

Awk читает со стандартного ввода. Когда вы запускаете awk, как вы делаете выше, скрипт awk будет обрабатывать stdin. Вы не передали его ни в один файл для обработки. Если у вас есть файл, например test.in, вы можете запустить свою программу awk следующим образом:

awk -v temp=hello -f test1.awk test.in 

Скрипт awk обработает test.in и завершит работу.

Надеюсь это поможет.

Спасибо, что я должен положить в test.in? dacfer 6 лет назад 0
Что вы пытаетесь сделать со своим сценарием awk? Lewis M 6 лет назад 0
Я пытаюсь использовать awk для интерпретации переменной среды, net_args: net_args = debug = (123,456), чтобы увидеть, есть ли% 1 там или нет. Если это так, то я выхожу из скрипта awk с выходом 1, иначе с выходом 0 dacfer 6 лет назад 0
поэтому я использую: awk -v "temp =% net_args%" -v dflag =% 1 -f test.awk test.in. Я положил мусор в test.in, и он работает, но мне просто интересно, каково значение test.in. dacfer 6 лет назад 0
Тогда вы можете ввести / dev / null или любой другой эквивалент в Windows. Lewis M 6 лет назад 0
В общем, awk используется для обработки текста, который обычно считывается из стандартного ввода и записывается в стандартный вывод. Если вам не нужен ни один из них, вы можете использовать / dev / null для ввода или вывода. Lewis M 6 лет назад 0
0
Matthias Gralle

Чтобы избежать бессмысленного ввода файла, вы можете поместить команды в предложение END:

END { x=temp; print x; } 

Затем вызовите сценарий awk с / dev / null для ввода, как это было предложено Льюисом М:

awk -v temp=hello -f test1.awk </dev/null 

Или эквивалентно в одну строку:

awk -v temp=hello 'END ' </dev/null 
0
Scott

Вы говорите, что хотите выполнить несколько операторов awk один раз, не требуя ввода данных пользователем, а затем остановитесь и вернитесь в командную строку. И в вашем случае вы говорите о командной строке ( cmd.exeв Windows), а не об оболочке (например, bash).

  1. Ответ Матиаса Глэра ,

    awk -v temp = привет 'END '</ dev / null

    будет работать в Unix / Linux и, возможно, даже в Unix-подобной оболочке в Windows, но не в cmd.exe. Windows не имеет /dev/null, по сути.   Но в Windows есть нулевое устройство, которое называется просто NUL. (Вы можете добавить двоеточие, в результате чего  NUL:, если хотите, это необязательно. И, как обычно в Windows, это без учета регистра, так что вы можете сказать nul.)

    awk -v temp = привет 'END '<nul
    вероятно будет работать.

    Вы не говорите, какой у awkвас вкус на вашем компьютере с Windows. У меня есть Cygwin, и получается, что я могу сделать

    C: \ Users \ scott> \ cygwin64 \ bin \ gawk -v temp = привет 'END '/ dev / null Привет
    Разница в том, что, когда вы говорите, командный процессор ( в вашем случае) обрабатывает имя файла, но, если вы пропустите и просто скажете, программа обрабатывает его. И оказывается, что программы Cygwin интерпретируют как нулевое устройство, даже если они запускаются из командной строки.< filenamecmd.exe<filename/dev/null

    Поскольку я не знаю, какой у awkвас вкус на вашем компьютере с Windows, я не знаю, сработает ли это для вас.

  2. Матиас подошел очень близко к тому, чтобы дать вам действительно хороший ответ. Как объяснил Льюис М, awk обрабатывает ввод. Типичная awk-программа выглядит примерно так
    НАЧАЛО { что-то делать (один раз) в начале программы } { что-то делать в каждой строке ввода } / foo / { что-то делать в каждой строке ввода, содержащей «foo» } { что-нибудь еще сделать в каждой строке } ︙ END { что-то сделать (один раз) в конце программы }
    где все эти части являются необязательными. (И, как вы продемонстрировали в своем вопросе, блоки кода (или действия) могут быть разбиты на несколько строк. И короткие вещи могут быть объединены в одной строке.) Идея Матиаса состоит в том, чтобы поместить ваши операторы в ENDкод блок, а затем для предоставления нулевого ввода, поэтому awk запустится, выполнит ваши операторы один раз, а затем завершится.   Не то чтобы с этим что-то не так. Но получается, что, если ваша программа состоит из BEGINблока кода, и больше ничего, то AWK выполняет ваше заявление (ы) (один раз), не пытаясь даже никакого ввода.   Так что можете сказать
    awk -v temp = привет 'BEGIN '
    и не нужно беспокоиться о предоставлении / указании каких-либо входных данных.
  3. Вот пример тривиальной программы awk, которая не слишком тривиальна:

    awk ''

    Если вы напечатаете это, а затем нажмете Enter, он скажет Hello. Если вы напечатаете world, он скажет Hello world. Если вы напечатаете Kitty, он скажет Hello Kitty© . Как вы знаете, вы можете вернуться в командную строку, нажав Ctrl+ C, что в основном означает «прерывание / остановка обработки». Но «приятнее» сделать это, нажав « CtrlD, что означает «это конец ввода». Это стандартно для Unix и Linux, но я могу сделать следующее (где bold italicтекст - то, что я напечатал):

    C: \ Users \ scott> \ cygwin64 \ bin \ gawk ' END '  моряк Привет моряк незнакомец Привет незнакомец Ctrl+ D До свидания
    тогда как, если я нажму Ctrl+ C, ENDкод не запустится.

    Опять же, если вы используете что-то другое, чем Cygwin, я не знаю, будет ли это работать для вас.


Во всех приведенных выше примерах все, что я помещаю между одинарными кавычками ( '…'), может быть помещено в файл, который вы (как вы знаете) вызываете . В Unix, Linux и Cygwin я предпочитаю помещать свои awk-программы в сценарии оболочки, например-f filename

#! / Bin / ш awk '' "$ @"
вместо того, чтобы использовать .awkфайлы. "$@"Позволяет передавать аргументы AWK. Возможно, вы сможете сделать это в пакетном файле Windows $*, но в Windows все не так просто.

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