web-dev-qa-db-ja.com

-cを介してbashに渡されたときにスクリプトが機能しない

なぜこれが機能するのですか?

$ cat test.sh
#!/bin/bash
cat <(date|awk '{print $1}')

$ ./test.sh
Thu

しかし、bashに渡されるコマンドとしては:

$ bash -c "cat <(date|awk '{print $1}')"
Thu  2 Apr 2020 12:52:10 BST

私はこれをmacOSで実行しています

$ bash --version
GNU bash, version 3.2.57(1)-release (x86_64-Apple-darwin19)
Copyright (C) 2007 Free Software Foundation, Inc.
6
Robin Moffatt

ワンライナーでは、_$1_は二重引用符で囲まれた文字列内にあります。

_"cat <(date|awk '{print $1}')"
_

これは、インタラクティブシェルによって展開されることを意味します。最初の位置パラメータ_$1_が空の場合、空の文字列に展開され、入力を出力するawkプログラムになります。

_awk '{print }'
_

_$_内の_$1_を_\$1_としてエスケープして、シェルが展開しようとするのを停止します。完全なコマンドは次のようになります

_bash -c "cat <(date|awk '{print \$1}')"
_

スクリプトバリアントでは、_$1_は単一引用符で囲まれた文字列です。したがって、シェルはそれを拡張しようとしません。

ただし、この特定のケースでは、

_date +%a
_

曜日の省略名を出力します。 strftime(3)マニュアル(_man 3 strftime_)も参照してください。

新しいbashバージョン(リリース4.2以降、つまり、macOSのdefaultbashではありませんが、例 Homebrew )を介してインストールされ、

_printf '%(%a)T\n' -1
_

外部コマンドを呼び出さずに同じことを行います。

22
Kusalananda