2012-05-25 2 views
26

У меня есть переменная $foo="something" и хотел бы использовать:Bash - переменные переменные

bar="foo"; echo $($bar) 

, чтобы получить «что-то» эхом.

+2

Пожалуйста, см [BashFAQ/006] (http://mywiki.wooledge.org/BashFAQ/006). Кроме того, вы не должны пытаться использовать знак доллара в левой части задания. –

ответ

51

В bash вы можете использовать $ {! Variable} для использования переменных переменных.

foo="something" 
bar="foo" 
echo "${!bar}" 
+0

Намного лучше, чем мой ответ. – mkb

+0

@mkb Я не знал eval :-) – dAm2K

+0

в 'sh' он говорит о плохой замене. Любая идея, как это сделать в 'sh'? –

5

eval echo \"\$$bar\" сделал бы это.

+5

Знайте о [последствиях безопасности 'eval'] (http://mywiki.wooledge.org/BashFAQ/048). –

+0

Это решение имеет преимущества совместимости с POSIX для оболочек, отличных от Bash (например, в таких легких средах, как встроенные системы или контейнеры Docker). И вы можете присвоить значение другой переменной следующим образом: '' 'ш вар = $ (Eval эхо \ "\ $$ бар \") ' '' –

6

Принятый ответ замечательный. Тем не менее, @Edison спросил, как сделать то же самое для массивов. Фокус в том, что вы хотите, чтобы ваша переменная держала «[@]», так что массив расширяется с помощью «!». Проверьте эту функцию, чтобы сбросить переменные:

$ function dump_variables() { 
    for var in "[email protected]"; do 
     echo "$var=${!var}" 
    done 
} 
$ STRING="Hello World" 
$ ARRAY=("ab" "cd") 
$ dump_variables STRING ARRAY ARRAY[@] 

Этот выход:

STRING=Hello World 
ARRAY=ab 
ARRAY[@]=ab cd 

Когда дано только как ARRAY, первый элемент отображается как это то, что расширяется за счет !. Предоставляя формат ARRAY[@], вы получаете массив и все его значения.

+0

Хороший вопрос об обработке массивов. Любая идея, как получить * индексы * массива? В [manual] (http://www.gnu.org/software/bash/manual/bashref.html#Shell-Parameter-Expansion) это обычно делается с помощью '$ {! ARRAY [@]}', что кажется для конфликта с синтаксисом переменной косвенности. – dimo414

+0

@ dimo414 Да, получить ключи через косвенность сложнее. Вам нужно будет передать только имя, затем выполнить расширение в методе: 'local -a 'keys = (" $ {!' "$ Var" '[@]} ")''. Статья [ссылка на Hashers Hashers] (http://wiki.bash-hackers.org/syntax/arrays#indirection) углубляется. – bishop

0

Для того, чтобы было более понятно, как это сделать с массивами:

arr=('a' 'b' 'c') 
# construct a var assigning the string representation 
# of the variable (array) as its value: 
var=arr[@]   
echo "${!var}" 
Смежные вопросы