
bash端末に直接貼り付けると、次のようになります(bash、bashバージョンを明示的に呼び出します4.4.19(1)-release (x86_64-pc-linux-gnu)
)
for filename in /home/dean/Downloads/!(*example).txt; do
echo "${filename}"
done
このコマンドは、ファイル名に「example」が含まれていないすべてのtxtファイルをエコーします。
しかし、それを名前の付いたスクリプトに変換し、temp.sh
次chmod +x temp.sh
のように呼び出すと./temp.sh
:
#!/usr/bin/env bash
for filename in /home/dean/Downloads/!(*example).txt; do
echo "${filename}"
done
次のエラーが発生します。
dean@dean-thinkpad-p52s:~/Downloads$ ./temp.sh
./temp.sh: line 3: syntax error near unexpected token `('
./temp.sh: line 3: `for filename in /home/dean/Downloads/!(*example).txt; do'
私はここで問題を理解していません。シェルでは私が望むことを正確に実行しますが、スクリプトでは何もしません。
編集(回答半期問題):
env
シェル/ターミナルから呼び出すときとenv
シェル/スクリプトで呼び出すときの違いは次のとおりです。
dean@dean-thinkpad-p52s:~/Downloads$ diff example_myshell.txt example_called_script.txt
5a6
> _=/usr/bin/env
36,37d36
< TERM=xterm-256color
< SHELL=/bin/bash
38a38,39
> SHELL=/bin/bash
> TERM=xterm-256color
45c46
< PYENV_SHELL=bash
---
> SHLVL=4
47c48
< SHLVL=3
---
> PYENV_SHELL=bash
61d61
< _=/usr/bin/env
答え1
Kornシェルスプレッド演算子は、このオプションをオンにした場合にのみ使用できます!(...)
(デフォルトではオフ)。bash
extglob
extglob
インタラクティブシェルから別の初期化ファイルを渡したか開いた可能性がありますが、~/.bashrc
これらのファイルはスクリプトの実行時にインポートされず、オプションは呼び出しシェルから継承されません(BASHOPTS
環境内の変数ではない限り)。そこに置くのは悪い考えです)。
明示的に開く
shopt -s extglob
スクリプトの冒頭で動作するはずです。
まだshopt -s extglob
解析されていない次の行からのみ有効です。これは、サブシェルでのみ拡張モードをオンにするためにshopt -s extglob
likeを使用できないことを意味します。set -f
# this won't work
(
shopt -s extglob
echo !(no such file)
)
次の作業を行う必要があります。
(
shopt -s extglob
eval 'echo !(no such file)'
)