スクリプトに初めて触れました。一部のテキストファイルを含むディレクトリがあり、一部のテキストファイルには追加の拡張子()も含まれています(.xfr
例:、、、)。file1.txt
file2.txt.xfr
file3.txt
file4.txt.xfr
bashスクリプトを作成してディレクトリを確認し、.xfr
ファイルに含まれている場合はファイル名を変更し(拡張子を削除)、結果に基づいてログエントリを作成します。
ファイルの名前を変更するスクリプトを書くことができますが、if
この部分に関して問題が発生しています。これは有効な部分です:
#!/bin/bash
for file in ~/Test/Files/*.xfr
do
mv "$file" "${file%.xfr}"
echo "$file has been resent" > ~/Test/log.txt
done
追加するにはif
これがうまくいくと思いましたが、残念ながらそうではありません。
#!/bin/bash
if [[ ! -e ~/Test/Files/*.xfr ]]
then
mv "$file" "${file%.xfr}"
echo "$file has been renamed" > ~/Test/log.txt
else
echo "no files were renamed" ~/Test/log.txt
fi
どんな助けでも大変感謝します。
更新:ファイルパスの代わりに変数を使用するようにスクリプトが更新されました。
#!/bin/bash
PATH='/home/davrog/Test/Files'
LOG='/home/davrog/Test/log.txt'
for file in $PATH/*.xfr
do
if [ -e $PATH/$file ]
then
mv "$file" "${file%.xfr}"
echo "$(date) $file has been resent"
else
echo "$(date) no files were stuck when check was run"
fi
done >>$LOG
これはmv関数を破壊するようです。ファイル名を現在の名前に変更し直すので疑います。他の投稿を見ると、mv関数が正しく見えますが、どのように解決するのかわかりません。助けてくれてありがとう。
答え1
最初のスクリプトを少し修正してください。
#!/bin/bash
for file in ~/Test/Files/*.xfr
do
if [ ! -e "$file" ]; then
echo 'no files were renamed'
break
fi
mv "$file" "${file%.xfr}"
echo "$file has been renamed"
done > ~/Test/log.txt
私はここで2つのことをしています。
done
ログファイルにリダイレクトすると、ループするたびにログファイルが切り捨てられ、ループ内のすべてのstdoutをリダイレクトするように最後に移動しました。パターンがファイル名と一致しない場合、デフォルトでは拡張されていません。テストによってこれを検出し
-e
、特別なメッセージを出力します。その後、break
ループを終了します。
選択する:
#!/bin/bash
for file in "$HOME/Test/Files"/*.xfr
do
if [ -e "$file" ]; then
mv "$file" "${file%.xfr}"
printf '%s has been renamed\n' "$file"
else
echo 'no files were renamed'
fi
done >"$HOME/Test/log.txt"
ここでは流れを少し変更し、$HOME
チルダの代わりに使用しました(IMHOはスクリプトでよりよく見えます)。私はまた、変数データを出力するのに通常より安全なので、printf
代わりに使用しますecho
(例:なぜprintfがechoより優れているのですか?")。
/bin/sh
上記の両方の選択肢を実行する代わりに使用することもできます/bin/bash
。
より多くの「レポート」を作成するには、他のオプションがあります。
#!/bin/bash
shopt -s nullglob
xfr_files=( "$HOME/Test/Files"/*.xfr )
for file in "${xfr_files[@]}"; do
mv "$file" "${file%.xfr}"
done
printf '%d files renamed\n' "${#xfr_files[@]}"
if [ "${#xfr_files[@]}" -gt 0 ]; then
printf '\t%s\n' "${xfr_files[@]}"
fi
これはnullglob
シェルオプションを設定し、bash
一致するものがない場合はパターンが空白に拡張されます。次に、名前が変更されたファイルの数を記録し、その数が0より大きい場合は、タブのインデントとともにファイル名も一覧表示します。
更新された質問から、変数を使用してくださいPATH
。これはシェルのユーティリティ検索パスを保持する変数なので、:
--separated ディレクトリのリスト以外に設定すると、シェルがmv
一般的に使用されている他のツールが見つからない場合があります。
通常、シェルスクリプトでは大文字の変数名を使用せず、代わりに小文字または大文字と小文字が混在する変数を使用します。これにより、シェルが使用できる重要な変数が誤って上書きされるのを防ぎます。
また、[ -e $PATH/$file ]
テストは[ -e "$file" ]
パスが値に含まれているため読み取る必要があります$file
。これは上記のコードでも私が使っているものです。すべての変数拡張を二重引用符で囲むことを忘れないでください!
答え2
prename
すでにインストールされている場合は、次のように実行できます。
prename 's/\.xfr$// and print "$_ resended\n"' ~/test/* > f.log