bashの部分文字列置換のシェルに依存しない同等のものがありますか?
foo=Hello
echo ${foo/o/a} # will output "Hella"
私が使うことができるほとんどの時間 bash
だからそれは問題ではありませんが、 find -exec
それは動作しません。たとえば、すべての名前を変更する .cpp
〜へのファイル .c
、私は使用したい:
# does not work
find . -name "*.cpp" -exec mv {} {/.cpp$/.c}
今のところ、私は以下を使用しています:
# does work, but longer
while read file; do
mv "$file" "${file/.cpp$/.c}";
done <<< $(find . -name "*.cpp")
スクリプトで使用できるソリューションが理想的です。
回答:
回答№1は4使用 find
そして -exec
あなたはこれを行うことができます:
find . -name "*.cpp" -exec bash -c "f="$1"; mv "$f" "${f/.cpp/.c}"" - "{}" ;
しかし、これはフォークします bash -c
使用する各ファイル名ごとに xargs
または for
このようなループはパフォーマンス上の理由から優れています。
while IFS= read -d "" -r file; do
mv "$file" "${file/.cpp/.c}"
done < <(find . -name "*.cpp" -print0)
回答№2の場合は1
Btw、代わりに使用する bash
使用するだろう rename
。あなたが クール バージョンの rename
コマンドは、一緒に出荷されます perl
できるよ:
find -name "*.cpp" -exec rename "s/.cpp$/.c/" {} +
上の例はあなたがGNUを所有していると仮定しています findutils
現在のディレクトリがデフォルトであるため、これを渡す必要はありません。もしあなたがGNUを持っていなければ findutils
それを明示的に渡す必要があります:
find . -name "*.cpp" -exec rename "s/.cpp$/.c/" {} +