次のように動的に名前付き変数を作成するとしますzsh
。
name="hello"
typeset $name=42
echo ${(P)${name}} # Prints the variable $hello, which is 42
それでは、誰かがその変数を増やしたり変更したりしていますが、直接名前がわからないとしましょう。つまり、次のようなものが機能したいと思います。
(( ${(P)${name}} = ${(P)${name}} + 1 )) # Set $hello to 43?
上記の方法は機能しません。何をしますか?
答え1
$ name=hello
$ hello=42
$ (($name++))
$ echo $hello
43
Kornのような殻のようなものです。またはPOSIXとして:
$ name=hello
$ hello=42
$ : "$(($name += 1))"
$ echo "$hello"
43
重要なのは、すべてのパラメータ拡張、コマンド置換、および算術拡張が算術式内で評価される前に実行されることです。
((something))
似ている
let "something"
したがって(($name++))
(例えばlet "$name++"
)では、まず変数に適用された演算子hello++
に展開され評価されます。++
hello
POSIXには演算子はsh
ありませんが、算術演算があります。((...))
$((...))
拡張オペレーター。そうではありませんが++
(実装時に単項演算子および/または二項演算子の組み合わせを必要とせずに拡張として持つことができますが+
)+=
。
: "$((...))"
where is nullコマンドを使用すると、:
kshに似た結果を得ることができます((...))
。厳密に同じですが、[ "$((...))" -ne 0 ]
式がゼロであると確認された場合、asはfalseを返します。((expression))
答え2
これはトリックを実行するようです:
typeset $name=$(( ${(P)${name}} + 1 ))
どんな代替案でも大変感謝いたします。