特定の拡張子のファイルがbashを使用してディレクトリに存在するかどうかをどのように判断しますか?
何かのようなもの
if [ -e *.flac ]; then
echo true;
fi
回答:
#!/bin/bash
count=`ls -1 *.flac 2>/dev/null | wc -l`
if [ $count != 0 ]
then
echo true
fi
ls -l
しています、私の答えは使用しますls -1
ls -1
ごとに1行を出力することはほぼ確実です
\n
(はい、ファイル名で有効です)。
#/bin/bash
myarray=(`find ./ -maxdepth 1 -name "*.py"`)
if [ ${#myarray[@]} -gt 0 ]; then
echo true
else
echo false
fi
${#myarray[@]}
が1に等しい結果を返さない場合
ls -1 *.py
検索の代わりに使用することで簡略化することもできます
これはls(1)を使用し、flacファイルが存在しない場合、lsはエラーを報告し、スクリプトは終了します。それ以外の場合、スクリプトは続行され、ファイルが処理される可能性があります
#! /bin/sh
ls *.flac >/dev/null || exit
## Do something with flac files here
if ls *.flac >/dev/null 2>&1; then ... fi;
shopt -s nullglob
if [[ -n $(echo *.flac) ]] # or [ -n "$(echo *.flac)" ]
then
echo true
fi
あなたはあなたがあなたのif
声明にどの旗を投げるか、そしてそれがあなたが望む結果にどのように関係しているかに注意を払う必要があります。
通常のファイルのみをチェックし、他のタイプのファイルシステムエントリはチェックしない場合は、コードスケルトンを次のように変更する必要があります。
if [ -f file ]; then
echo true;
fi
を使用すると、-f
はif
通常のファイルに制限されますが、-e
より拡張性が高く、すべてのタイプのファイルシステムエントリに一致します。もちろん-d
、ディレクトリなどの他のオプションもあります。適切なリストについては、http://tldp.org/LDP/abs/html/fto.htmlを参照してください。
@mswで指摘されているように、複数の引数を指定しようとすると、test
(つまり[
)がチョークします。これは、のglobが*.flac
複数のファイルを返した場合に発生する可能性があります。その場合if
は、次のようなループでテストをラップしてみてください。
for file in ./*.pdf
do
if [ -f "${file}" ]; then
echo 'true';
break
fi
done
このようにbreak
して、必要なファイル拡張子の最初のインスタンスで、スクリプトの残りの部分を続行できます。
test
(aka [
)は、パターンが複数のファイルに展開される場合に文句を言います:「二項演算子が必要です」または「引数が多すぎます」
"$file"
ファイル名にスペースやアスタリスクなどの不適切な文字が含まれている可能性があるため、変数を引用符で囲むか、を使用する必要があります。
一番上の解決策(if [ -e *.flac ];)
は私にはうまくいきませんでした:[: too many arguments
if ls *.flac >/dev/null 2>&1;
その後、それは動作します。
-fを使用して、特定のタイプのファイルが存在するかどうかを確認できます。
#!/bin/bash
if [ -f *.flac ] ; then
echo true
fi
[
(より一般的なものとは対照的に[[
)シングルブレースがグロブを防止しないためです。
shopt -s nullglob
set -- $(echo *.ext)
if [ "${#}" -gt 0 ];then
echo "got file"
fi
-ge
代わりに意味し-gt
ます。そうしないと、コードが単一のファイルを検出しないためです。次に、パターンに一致するファイルがない場合、準拠するシェルは文字列を*.ext
そのままにしておくため、1つの「結果」が得られます。
これは、外部コマンドを使用せず(つまり、no ls
)、代わりにシェル関数を使用するソリューションです。bashでテスト済み:
shopt -s nullglob
function have_any() {
[ $# -gt 0 ]
}
if have_any ./*.flac; then
echo true
fi
この関数have_any
は、$#
を使用して引数をカウントし[ $# -gt 0 ]
、少なくとも1つの引数があるかどうかをテストします。の呼び出し./*.flac
だけでなくの使用は、のような名前のファイルによって引き起こされる問題を回避することです。*.flac
have_any
--help
これはかなり簡単な解決策です:
if [ "$(ls -A | grep -i \\.flac\$)" ]; then echo true; fi
ご覧のとおり、これは1行のコードですが、十分に機能します。これは、bashと、dashのようなposix準拠のシェルの両方で機能するはずです。また、大文字と小文字は区別されず、どのタイプのファイル(通常、シンボリックリンク、ディレクトリなど)が存在するかは関係ありません。これは、シンボリックリンクなどがある場合に役立ちます。
私はこれを試しました:
if [ -f *.html ]; then
echo "html files exist"
else
echo "html files dont exist"
fi
このコードを他のファイルには問題なく使用しましたが、htmlファイルにはエラーが発生しました:
[: too many arguments
次に、@ JeremyWeirのカウントソリューションを試しました。
ループでこれを行う場合は、カウントをリセットする必要があることに注意してください。
count=$((0))
これは、そこにあるあらゆるボーンのようなシェルで機能するはずです。
if [ "$(find . -maxdepth 1 -type f | grep -i '.*\.flac$')" ]; then
echo true
fi
これはGNUでも機能しますがfind
、他の実装と互換性がある場合はIDK find
:
if [ "$(find . -maxdepth 1 -type f -iname \*.flac)" ]; then
echo true
fi