В сценарии оболочки, если я определяю переменную, такую как FOO=25
, есть ли разница между ссылками на нее как $FOO$
и ${FOO}$
?
command-line
scripts
Karnivaurus
источник
источник
$
в конце концов! Он будет обрабатываться как обычный символ, а не как часть имени переменной.Ответы:
В большинстве ситуаций оба
$var
и${var}
одинаковы. (Обратите внимание, что вы не должны использовать$
в конце!)Один пример, где вам нужны фигурные скобки, - это когда вам нужно поместить переменную в непрерывную строку.
Пример:
будет выводить
hello
.источник
Чтобы ответить на ваш главный вопрос,
${foo}
это называется «расширение параметров» . Чтобы быть точным,$
сам запускает расширение параметров,{ }
они на самом деле необязательны в соответствии со спецификацией POSIX , но могут быть полезны для указания конца имени переменной:В основном
$foo
и${foo}
идентичны. За исключением случаев, подобных описанному выше, или когда вы выполняете манипуляции со строками , они полностью эквивалентны.Тем не менее, вы не должны использовать ни один из них. Эмпирическое правило заключается в том, что, за очень немногими исключениями, вы должны всегда использовать
"$foo"
или"${foo}"
и никогда$foo
или${foo}
. Вы всегда должны заключать в кавычки свои переменные, чтобы избежать вызова оператора split + glob (подробнее об этом позже). Вы, конечно, не хотите$foo$
. Финал не$
имеет значения:Итак, в то время как переменные без кавычек иногда в порядке:
Их обычно нет, и их действительно следует избегать:
Обратите внимание, что скобки здесь тоже не помогают:
Когда вы используете
$foo
или${foo}
, оболочка разделяет значение, сохраненное в переменной на пустое пространство (это можно изменить, установивIFS
переменную в другое значение), в список, а затем каждый элемент списка обрабатывается как глобальный шаблон и разворачивается в любые соответствующие файлы или каталоги. Это известно как оператор split + glob . Для иллюстрации рассмотрим каталог с двумя файлами:Теперь давайте установим переменную в
foo *
:Что произойдет, если мы попытаемся проверить, существует ли файл с таким именем?
Переменная была разбита на
foo
и*
и, поскольку*
это подстановочный знак, который соответствует любой строке, оболочка сообщает вам, что файл называетсяfoo *
exxists. Однако, если мы процитируем это правильно, этого не произойдет:Это был тривиальный пример, чтобы проиллюстрировать это. Представь, если бы я использовал
rm
вместо этого,echo
хотя.Итак, первое правило: всегда указывайте свои переменные. Вы можете использовать либо
"$foo"
или,"${foo}"
но процитировать его в любом случае. Чтобы узнать больше о безопасном использовании переменных, взгляните на эти сообщения:источник
$ var="foo *"
ли$ foo="foo *"
? Вы не используетеvar
нигде.