我的./
文件夹下有一些文件,例如:
$ ls
XX
AArse
BArse
CCCAArse
YY
....
在某些命令之后,我想要:
AA
BA
CCCAA
即如果文件名的末尾包含rse
,则文件将被重命名(以从其名称中删除rse
)。
如何在bash中实现某些命令?
使用bash
:
shopt -s nullglob
for file in *rse; do
mv -i "$file" "${file%rse}"
done
shell选项nullglob
将不匹配的glob模式扩展为空字符串,参数扩展${file%rse}
从文件名中删除最短的后缀rse
。
选项-i
提示覆盖已经存在的文件。
使用Perl的独立rename
命令,正则表达式和bash的globbing:
rename -n 's/...$//' *rse
在某些发行版中,rename
也称为prename
。如果一切正常,请删除-n
。
给出一个稍微通用的答案:
finder.sh:
#!/usr/bin/env bash
usage() {
echo 'Usage: ./finder.sh string_to_remove'
exit
}
if [ "$#" -ne 1 ]; then
usage
fi
check_string=$1
counter=0
for file in ./*
do
if [[ -f $file ]]; then
if [[ $file == *"$check_string"* ]]; then
mv -v "$file" `echo $file | sed "s/$check_string//"`
let "counter++"
fi
fi
done
if [ ! "$counter" -gt 0 ]; then
echo "No files found containing '$check_string'"
else
echo "$counter files effected with string '$check_string'"
fi
然后您可以通过以下方式(在执行chmod +x finder.sh
之后,将其与其他子字符串一起使用:]
./finder.sh any_string
# Removes 'any_string' from all filenames
带有以下目录列表:
$ ls
AArse
AByfl
BArse
CCCAArse
XX
YY
您可以跑步
./finder.sh rse; ./finder.sh yfl
获得以下输出:
renamed './AArse' -> './AA'
renamed './BArse' -> './BA'
renamed './CCCAArse' -> './CCCAA'
3 files effected with string 'rse'
renamed './AByfl' -> './AB'
1 files effected with string 'yfl'
这样您的目录现在看起来像:
AA
AB
BA
CCCAA
XX
YY
当然,使用mv
命令时,您可能希望对某些潜在的覆盖进行检查。