Как следующий сценарий может быть объяснен?

[1180740] Попробуйте эту [1181060]awk[1181061] команду,

1
28.08.2014, 19:09
4 ответа

Гнук делает важное замечание, не подчеркивая его: всякий раз, когда вы ссылаетесь на переменную оболочки ( $ идентификатор , например, $ futur ) или позиционный параметр ( $ цифра , например, $ 1 ), вы должны заключить его в двойные кавычки (например, "$ 1" ), если у вас нет веской причины не и вы совершенно уверены, что знаете, что делаете. Постоянные строки без специальных символов (например, A , foo или bar ) цитировать не нужно, но это не повредит. Строки в кавычках можно объединять и комбинировать; например, «foo» «bar» эквивалентно «foobar» , и «$ 1» эквивалентно «A» «$ 1» и, следовательно, «A $ 1» .

  • Цитаты сохраняют существование пустых строк. Как объясняет Гноук, если в вашем скрипте указано

     if ($ 1 == "")
     

    и вы вызываете его без аргументов,

     СПИСОК
     

    или с явным аргументом пустой строки,

     LIST ""
     

    , тогда оператор if будет «развернут» как

     if (== "")
     

    , что вызывает синтаксическую ошибку.

  • Кавычки сохраняют целостность строк с пробелами или специальными символами. Если вы вызываете свой скрипт с аргументом, содержащим пробел,

     LIST "foo bar"
     

    , то оператор if ( if (A $ 1 == A) ) будет расширен как

     if (Afoo bar == A)
     

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

     LIST "foo *"
     

Но никто не объяснил, почему сценарий не просто говорит

if ( "$1" == "" )

В предыдущих версиях csh , если вы вызываете свой сценарий с этим аргументом,

LIST ==

тогда Оператор if будет расширен как

if ( "==" == "" )

, что также вызвало синтаксическую ошибку. Люди писали свои if операторы с защитой позиционных параметров. (и, при необходимости, переменные оболочки / переменные среды), например A $ 1 или «A $ 1» , чтобы аргументы (операнды) не выглядели как операторы (в частности, / , также + , - и * ), что приводит к путанице анализатора. Кажется, это было исправлено (по крайней мере, в некоторых версиях csh / tcsh ). Я только что попробовал это в своей (Cygwin) версии tcsh :

$ if ( == == "" ) echo yes
if: Expression Syntax.
$ if ( == == == ) echo yes
if: Expression Syntax.
$ if ( "==" == "" ) echo yes
                                <--- (no output)
$ if ( "==" == "==" ) echo yes
yes
$ if ( / == / ) echo yes
Division by 0.
$ if ( "/" == "/" ) echo yes
yes

так,

  • Quotes может сообщить команде if в tcsh , что аргумент это операнд а не оператор.
0
27.01.2020, 23:20

Убедитесь, что $1 - это не пустая строка. Если $1 пустая строка, то если условие:

( A == A )

оценивается как истинное. Это обходной путь, чтобы убедиться, что у вас нет синтаксической ошибки. Если просто сделать:

if ( $1 == "" )

Когда $1 пустая строка, то это выражение становится ( == "" ) и приводит к синтаксической ошибке.

Как минимум в bsd-csh, tcsh, ( $1 == "" ) работает. С оригинальным csh следует использовать:

if ( "A$1" == "A" )

Заметку о том, что Вы всегда должны заключать в кавычки двойную переменную, см. объяснение здесь. В csh, если переменная $a содержит newline, то "$a" не сработает, Вам нужно $a:q.

4
27.01.2020, 23:20

В этой строке проверяется, пуст ли 1 . $1 - это первый параметр, переданный пользователем скрипту при выполнении скрипта в командной строке. Если $1 пустой, то к букве A ничего не добавляется и A == A истинно.

0
27.01.2020, 23:20

Я считаю, что цикл if используется как способ проверить, переданы ли аргументы сценарию или нет. Хотя технически это цель цикла if , я думаю, было бы более уместно сказать, что он используется для проверки, является ли $ 1 пустым или нет. Например, я скопировал сценарий и вызвал его как,

script "some_argument"

Как и ожидалось, он не входит в цикл if . Теперь, если я вызываю его без каких-либо параметров как,

script

, я получаю вывод как LIST

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

Кроме того, A $ 1 == A - это просто то, что нужно для проверки, является ли $ 1 пустым или нет. Даже если у вас есть что-то вроде, somethingvalid $ 1 == somethingvalid и вы вызываете сценарий как script , он все равно попадет в цикл if и распечатает результат.

0
27.01.2020, 23:20

Теги

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