Bashサブシェルに関するより詳細な情報を調べている間、それがどのように機能するかを理解したい興味深い実装を見つけました。実行には変数に文字列を割り当て、次の場合にその変数を使用する操作が含まれますman
。オリジナルの例リンク。LESS
この例では特定の変数が使用されている理由(多くのディストリビューションのデフォルトman
ポケットベル)を読みましたがless
、コマンドの実行後に変数の割り当てがどのような区切りメタ文字なしで機能するかを理解できません。
LESS=+/'OPTIONS' man man
man
そのセクションのすぐ下にあるコマンドのマニュアルページを開きますOPTIONS
。あまりにも直接開いているファイルで動作します(これは変数が「セッション」内で正規表現検索を実行するのと同じ方法で使用されるとless
信じます)。変数はエクスポートされず、現在のシェル環境には保存されません(実行時に何も返しません)。では、どのように値をキャプチャしますか?LESS
less
less
LESS
echo $LESS
less
なぜこれはうまくいきますが、それはうまくいきませんかfoo='hello' echo $foo
?;
これは、変数の割り当てとコマンド実行の間にコマンド区切り文字()がある場合にのみ機能します。foo=+'hello' echo $foo
分からないので、=+
Bashで何かを試してみましたが、結果は変わりませんでした。
どんな説明や読書も歓迎します!
答え1
これは標準機能です。コマンドの起動時にこの変数を設定できます。これにより、そのコマンドに設定されます。また、示した例でも機能しますfoo='hello' echo $foo
。問題は、間違った方法でテストしていることです。これを実行すると:
foo='hello' echo $foo
シェルは変数を拡張します今後コマンドを実行します。実際に起動時に設定されないため(エコーなし)にfoo
なります。echo
以下で見ることができますset -x
。
$ set -x
$ foo='hello' echo $foo
+ foo=hello
+ echo
次に、小さなスクリプトを使用して変数をシェルに見えないようにするときに発生する状況と比較します。
$ cat ~/scripts/foo.sh
+ cat /home/terdon/scripts/foo.sh
#!/bin/bash
echo "The value of foo is:$foo"
これを使用して変数をエコーすると、次のようになります。
$ foo='hello' ~/scripts/foo.sh
+ foo=hello
+ /home/terdon/scripts/foo.sh
The value of foo is:hello
bash -c
与えられたコマンドを呼び出して一重引用符で囲むと、同じことができます。これにより、呼び出し前に変数が保護され、現在のシェルによって拡張されませんbash -c
。
$ foo='hello' bash -c 'echo $foo'
hello
$foo
ただし、二重引用符は表示される前に拡張されたことを意味するため失敗しますbash -c
。
$ foo='hello' bash -c "echo $foo"
$
この動作はman bash
「環境」セクションで説明されています。
The environment for any simple command or function may be augmented
temporarily by prefixing it with parameter assignments, as described
above in PARAMETERS. These assignment statements affect only the envi‐
ronment seen by that command.
マニュアルにも詳細な説明があります。3.7.1 簡単なコマンド拡張