Разница между одинарными и двойными кавычками в Bash

337

В Bash, каковы различия между одинарными кавычками ('') и двойными кавычками ("")?

Теги:
syntax
quotes

6 ответов

351
Лучший ответ

Одиночные кавычки не будут интерполировать ничего, но двойные кавычки будут. Например: переменные, обратные выходы, определенные \ и т.д.

Пример:

$ echo "$(echo "upg")"
upg
$ echo '$(echo "upg")'
$(echo "upg")

В руководстве Bash есть следующее:

3.1.2.2 Отдельные кавычки

Закрывающиеся символы в одинарных кавычках (') сохраняют буквальное значение каждого символа в кавычках. Одинарная кавычка может отсутствовать между одинарными кавычками, даже если ей предшествует обратная косая черта.

3.1.2.3 Двойные котировки

Закрывающие символы в двойных кавычках (") сохраняют буквальное значение всех символов в кавычках, за исключением $, ', \, и, когда расширение истории включено ! Символы $ и ' сохраняют свое особое значение в двойном (см. раздел "Расширения оболочки"). Обратная косая черта сохраняет свое особое значение только тогда, когда следует один из следующих символов: $, ', ", \ или newline. В двойных кавычках удаляются обратные косые следы, сопровождаемые одним из этих символов. Обратные косые черты, предшествующие символам без особого значения, остаются неизмененными. Двойная кавычка может быть заключена в двойные кавычки, предшествуя ей обратным слэшем. Если включено, расширение истории будет выполнено, если только ! появляется в двойных кавычках, с помощью обратной косой черты. Обратная косая черта, предшествующая ! не удаляется.

Специальные параметры * и @ имеют особое значение, когда в двойных кавычках (см. Расширение параметров оболочки).

  • 12
    Для тех, кто не знает, что означает «интерполировать»: en.wikipedia.org/wiki/String_interpolation
  • 0
    Как насчет того, когда вы используете git_prompt который предоставляет git, они предлагают использовать его следующим образом: PS1='[\u@\h \W$(__git_ps1 " (%s)")]\$ ' , приглашение git , в соответствии с этим не работает Есть ли что-то особенное в переменных PS# ? или почему это работает, если он не выполняет интерполяцию.
Показать ещё 1 комментарий
193

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

Например, этот

#!/bin/sh
MYVAR=sometext
echo "double quotes gives you $MYVAR"
echo 'single quotes gives you $MYVAR'

даст следующее:

double quotes gives you sometext
single quotes gives you $MYVAR
139

Принятый ответ велик. Я делаю таблицу, которая помогает в быстром понимании темы. Объяснение включает в себя простую переменную a а также индексированный массив arr.

Если мы установим

a=apple      # a simple variable
arr=(apple)  # an indexed array with a single element

а затем echo выражение во втором столбце, мы получим результат/поведение, показанное в третьем столбце. В четвертой колонке объясняется поведение.

 # | Expression  | Result      | Comments
---+-------------+-------------+--------------------------------------------------------------------
 1 | "$a"        | apple       | variables are expanded inside ""
 2 | '$a'        | $a          | variables are not expanded inside ''
 3 | "'$a'"      | 'apple'     | '' has no special meaning inside ""
 4 | '"$a"'      | "$a"        | "" is treated literally inside ''
 5 | '\''        | **invalid** | can not escape a ' within ''; use "'" or $'\'' (ANSI-C quoting)
 6 | "red$arocks"| red         | $arocks does not expand $a; use ${a}rocks to preserve $a
 7 | "redapple$" | redapple$   | $ followed by no variable name evaluates to $
 8 | '\"'        | \"          | \ has no special meaning inside ''
 9 | "\'"        | '           | \' is interpreted inside ""
10 | "\""        | "           | \" is interpreted inside ""
11 | "*"         | *           | glob does not work inside "" or ''
12 | "\t\n"      | \t\n        | \t and \n have no special meaning inside "" or ''; use ANSI-C quoting
13 | "'echo hi'" | hi          | '' and $() are evaluated inside ""
14 | ''echo hi'' | 'echo hi'   | '' and $() are not evaluated inside ''
15 | '${arr[0]}' | ${arr[0]}   | array access not possible inside ''
16 | "${arr[0]}" | apple       | array access works inside ""
17 | $'$a\''     | $a'         | single quotes can be escaped inside ANSI-C quoting
18 | "$'\t'"     | $'\t'       | ANSI quoting is not interpreted inside ""
19 | '!cmd'      | !cmd        | history expansion character '!' is ignored inside ''
20 | "!cmd"      | cmd args    | expands to the most recent command matching "cmd"
---+-------------+-------------+--------------------------------------------------------------------

Смотрите также:

  • 1
    Принятый ответ в конце говорит: The special parameters * and @ have special meaning when in double quotes так, как получается, что "*" приводит к * ?
  • 2
    @ Karl-AnderoMere, потому что в этом случае они вообще не раскрываются как параметры. "$@" и "$*" являются расширениями параметров. "@" и "*" не являются.
Показать ещё 3 комментария
2

Другие объясняли очень хорошо и просто хотели дать простые примеры.

Одиночные кавычки могут использоваться вокруг текста, чтобы предотвратить интерпретацию оболочкой каких-либо специальных символов. Знаки доллара, пробелы, амперсанды, звездочки и другие специальные символы игнорируются при включении в одинарные кавычки.

$ echo 'All sorts of things are ignored in single quotes, like $ & * ; |.' 

Это даст следующее:

All sorts of things are ignored in single quotes, like $ & * ; |.

Единственная вещь, которая не может быть помещена в одинарные кавычки, - это одиночная цитата.

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

$ echo "Here how we can use single ' and double \" quotes within double quotes"

Это даст следующее:

Here how we can use single ' and double " quotes within double quotes

Также можно заметить, что апостроф, который иначе интерпретируется как начало цитируемой строки, игнорируется в двойных кавычках. Переменные, однако, интерпретируются и заменяются их значениями в двойных кавычках.

$ echo "The current Oracle SID is $ORACLE_SID"

Это даст следующее:

The current Oracle SID is test

Обратные кавычки полностью отличаются от одиночных или двойных кавычек. Вместо того, чтобы использоваться для предотвращения интерпретации специальных символов, обратные кавычки фактически вынуждают выполнение команд, которые они заключают. После выполнения прилагаемых команд их вывод заменяется вместо обратных кавычек в исходной строке. Это будет более ясным с примером.

$ today='date '+%A, %B %d, %Y''
$ echo $today 

Это даст следующее:

Monday, September 28, 2015 
0

Существует четкое различие между использованием ' ' и " ".

Когда ' ' используется во всем, нет "трансформации или перевода". Он печатается так, как есть.

С " ", независимо от того, что он окружает, "переводится или преобразуется" в его ценность.

Под трансляцией/преобразованием я имею в виду следующее: все, что содержится в одинарных кавычках, не будет "переведено" на их значения. Они будут приняты, поскольку они находятся внутри кавычек. Пример: a=23, тогда echo '$a' будет генерировать $a на стандартном выходе. В то время как echo "$a" произведет 23 на стандартном выходе.

  • 1
    Что вы подразумеваете под «переводом» или «трансформацией»?
  • 0
    Этот ответ довольно запутанный, и он ничего не добавляет к существующим хорошим ответам.
-5

Помимо интерполяции одиночная кавычка также используется для преобразования вывода комманда в строку.

Например, Если вы хотите использовать результат из lynx --dump www.example.com|grep "something" в другой программе, скажем, филе, вы можете использовать одинарные кавычки, чтобы упростить вашу работу вместо копирования и вставки (что, в свою очередь, невозможно в сценариях).

#!/bin/sh
figlet "`lynx --dump www.example.com|grep "something" `"

Ещё вопросы

Сообщество Overcoder
Наверх
Меню