最近、業務でシェルスクリプトを書く機会が多かったのですが、なるべく汎用的に使える関数にしたいし、グローバル変数も使用したくないので、どうにか参照渡しのようなことが出来ないか調べてみたところ、evalコマンドを使うと実現可能だということが分かったので紹介します。
evalコマンドとは
指定した文字列を評価後に連結して、現在のシェルに実行させることができるコマンドです。
www.atmarkit.co.jp
参照渡しもどきをやるにはどうすればいいのか?
evalコマンドで、設定したい変数名を格納した変数を左辺に設定し、設定した値を右辺に設定することで参照渡しもどきが可能です。
eval "${設定したい変数名を格納した変数}=設定したい値"
下記がサンプルコードになります。
isNotEmptyAndGetValue関数の第2パラメータに変数名(str2)を渡しています。
isNotEmptyAndGetValue関数でevalコマンドを利用してstr2変数に値を設定します。
#!/bin/bash function isNotEmptyAndGetValue() { local str="$1" local valueKey="$2" if [[ -z ${str} ]] ; then return 1 fi # 参照渡しもどき? eval "${valueKey}=$(echo ${str} | awk -F= '{print $2}')" return 0 } function main() { local str1="" isNotEmptyAndGetValue "" str1 echo "\$?=$? \$str1=${str1}" local str2="" isNotEmptyAndGetValue "key=aaa" str2 echo "\$?=$? \$str2=${str2}" } main
valueKeyにstr2変数名が設定されており、evalコマンドによってvalueKey変数がstr2へ展開されます。
これが。
eval "${valueKey}=$(echo ${str} | awk -F= '{print $2}')"
こうなる。
eval str2=aaa