为所有没有特定扩展名的文件添加后缀并保留文件扩展名

为所有没有特定扩展名的文件添加后缀并保留文件扩展名

我有一个包含.zip文件和其他文件的目录(所有文件扩展名),我想为所有文件添加后缀没有扩展.zip名。我能够挑选一个后缀并将其放入变量中$suffix,因此我尝试了以下代码:

ls -I "*.zip"| xargs -I {} mv {} {}_"$suffix"

这列出了所有没有.zip且 接近的文件(但错误)。它错误地在 上产生以下结果file.csv

file.csv_suffix

我想file_suffix.csv——如何编辑我的代码以保留文件的扩展名?

答案1

使用起来ls有点危险。看为什么*不*解析`ls`?

您还必须分开文件名,否则您只需附加$suffix到它的末尾,正如您发现的那样。

以下是使用find和不使用 的解决方案find


find . -type f ! -name '*.zip' -exec sh -c 'suffix="$1"; shift; for n; do p=${n%.*}; s=${n##*.}; [ ! -e "${p}_$suffix.$s" ] && mv "$n" "${p}_$suffix.$s"; done' sh "$suffix" {} +

这将找到当前目录中或当前目录下某处的所有常规文件,其名称不以.zip.

然后将使用这些文件的列表调用以下 shell 脚本:

suffix="$1"  # the suffix is passed as the first command line argument
shift        # shift it off $@
for n; do    # loop over the remaining names in $@
    p=${n%.*}    # get the prefix of the file path up to the last dot
    s=${n##*.}   # get the extension of the file after the last dot

    # rename the file if there's not already a file with that same name
    [ ! -e "${p}_$suffix.$s" ] && mv "$n" "${p}_$suffix.$s"
done

测试:

$ touch file{1,2,3}.txt file{a,b,c}.zip
$ ls
file1.txt file2.txt file3.txt filea.zip fileb.zip filec.zip

$ suffix="notZip"
$ find . -type f ! -name '*.zip' -exec sh -c 'suffix="$1"; shift; for n; do p=${n%.*}; s=${n##*.}; [ ! -e "${p}_$suffix.$s" ] && mv "$n" "${p}_$suffix.$s"; done' sh "$suffix" {} +

$ ls
file1_notZip.txt    file3_notZip.txt    fileb.zip
file2_notZip.txt    filea.zip           filec.zip

find如果文件数量不是很大并且不需要递归到子目录(只需稍微修改以跳过非文件名),上面的 shell 脚本就可以独立运行:

#!/bin/sh

suffix="$1"  # the suffix is passed as the first command line argument
shift        # shift it off $@
for n; do    # loop over the remaining names in $@

    [ ! -f "$n" ] && continue  # skip names of things that are not regular files

    p=${n%.*}    # get the prefix of the file path up to the last dot
    s=${n##*.}   # get the extension of the file after the last dot

    # rename the file if there's not already a file with that same name
    [ ! -e "${p}_$suffix.$s" ] && mv "$n" "${p}_$suffix.$s"
done

使用bash,您可以对目录中的文件运行此命令,如下所示:

$ shopt -s extglob
$ ./script.sh "notZip" !(*.zip)

通过extglob在 中设置 shell 选项bash!(*.zip)将匹配当前目录中不以 结尾的所有名称.zip

答案2

寻找+巴什方法:

export suffix="test"

A)与查找-exec操作:

find your_folder -type f ! -name "*.zip" -exec bash -c 'f=$1; if [[ "$f" =~ .*\.[^.]*$ ]]; then ext=".${f##*\.}"; else ext=""; fi; mv "$f" "${f%.*}_$suffix$ext"' x {} \;


) 或者使用 bashwhile循环:

find your_folder/ -type f ! -name "*.zip" -print0 | while read -d $'\0' f; do 
    if [[ "$f" =~ .*\.[^.]*$ ]]; then
        ext=".${f##*\.}"
    else 
        ext=""
    fi
    mv "$f" "${f%.*}_$suffix$ext"
done

答案3

在bash中:

shopt -s extglob
suffix=yoursuffix
for entry in !(*.zip)
do
  [[ -f "$entry" ]] || continue
  base=${entry%.*}
  if [[ "$entry" =~ \. ]]
  then
    ext=${entry##*.}
    echo mv -- "$entry" "${base}_${suffix}.${ext}"
  else
    echo mv -- "$entry" "${base}_${suffix}"
  fi
done

echo当您觉得合适时将其删除。

测试用例:

touch a.zip b.zip foo bar file.csv a.file.csv 'test case' 'test case.csv'
mkdir baz

示例输出:

mv -- a.file.csv a.file_yoursuffix.csv
mv -- bar bar_yoursuffix
mv -- file.csv file_yoursuffix.csv
mv -- foo foo_yoursuffix
mv -- scr scr_yoursuffix
mv -- test case test case_yoursuffix
mv -- test case.csv test case_yoursuffix.csv

...跳过目录baz,但适当地重命名 foo 和 bar 。

答案4

for f in `ls -I "*.zip" `; do mv $f `echo $f | cut -d '.' -f1`_suffix.`echo $f | cut -d '.' -f2` ; done ;

其他有趣的工具包括实用程序,例如改名

这是一个有趣的问题,但这也意味着它可能已经被很多时间注意我保留了操作的 ls,它不排除目录。

相关内容