Как правильно вложить Bash backticks

Либо я пропустил какой-то люфт, либо обратный поток, похоже, не работает со слишком большим количеством циклов программирования-цитат.

$ echo "hello1-`echo hello2-\`echo hello3-\`echo hello4\`\``"

hello1-hello2-hello3-echo hello4

Требуются

hello1-hello2-hello3-hello4-hello5-hello6-...

Ответ 1

Вместо этого используйте $(commands):

$ echo "hello1-$(echo hello2-$(echo hello3-$(echo hello4)))"
hello1-hello2-hello3-hello4

$(commands) делает то же самое, что и backticks, но вы можете их вложить.

Вы также можете быть заинтересованы в расширении диапазона Bash:

echo hello{1..10}
hello1 hello2 hello3 hello4 hello5 hello6 hello7 hello8 hello9 hello10

Ответ 2

если вы настаиваете на использовании обратных ссылок, следующее может быть выполнено

$ echo "hello1-`echo hello2-\`echo hello3-\\\`echo hello4\\\`\``"

вам нужно поставить обратную косую черту, \\ \\\\ \\\\\\\\ на 2x и т.д., ее просто очень уродливо, используйте $(commands), как и другие.

Ответ 3

В любое время, когда вы хотите оценить команду, используйте command substitution:

$(command)

В любое время, когда вы хотите оценить арифметическое выражение, используйте expression substitution:

$((expr))

Вы можете вложить их так:

Скажем, файл file1.txt имеет длину 30 строк и файл2.txt имеет длину 10 строк, чем вы можете оценить выражение, подобное этому:

$(( $(wc -l file1.txt) - $(wc -l file2.txt) ))

который будет выводить 20 (разница в количестве строк между двумя файлами).

Ответ 4

Это намного проще, если вы используете bash $(cmd) синтаксис подстановки команд, который гораздо более дружелюбен к вложенности:

$ echo "hello1-$(echo hello2-$(echo hello3-$(echo hello4)))"
hello1-hello2-hello3-hello4

Ответ 5

Иногда вложенность backtick может быть заменена на xargs и pipe

$ echo hello4 | xargs echo hello3 | xargs echo hello2 | xargs echo hello1
hello1 hello2 hello3 hello4

Недостатками этого решения являются:

  • Все аргументы должны быть представлены в обратном порядке (4 → 1);
  • Все аргументы разделяются пробелами (решаются с помощью tr):

    $ echo hello4 | xargs echo hello3 | xargs echo hello2 | xargs echo hello1 | tr ' ' '-'
    hello1-hello2-hello3-hello4
    


Позвольте показать реальный вариант использования.

Следующие команды работают в bash, но не в tcsh (в tcsh вложенность обратных тиков не очень хорошо обрабатывается)

$ ls $(dirname $(which bash))
$ ls 'dirname \'which bash\''

Они могут быть заменены

$ which bash | xargs dirname | xargs ls