在Bash中,如何删除目录中文件名中的所有数字,同时保持文件扩展名不变

nub*_*ube 2 macos bash

我在这样的目录中有文件:

asdfs54345gsdf.pdf
gsdf6456wer.pdf
oirt4534724wefd.pdf
Run Code Online (Sandbox Code Playgroud)

我想将所有文件重命名为数字+ .pdf,以便上述文件重命名为:

54345.pdf
6456.pdf
4534724.pdf
Run Code Online (Sandbox Code Playgroud)

最好的是本机Bash命令或脚本(OSX 10.6.8)

我收到的一些线索包括

sed 's/[^0-9]*//g' input.txt 
sed 's/[^0-9]*//g' input.txt > output.txt 
sed -i 's/[^0-9]*//g' input.txt 
echo ${A//[0-9]/} rename 's/[0-9] //' *.pdf 
Run Code Online (Sandbox Code Playgroud)

use*_*own 6

这可以做到:

for f in *.pdf 
do 
   mv "$f" "${f//[^0-9]/}.pdf"
done
Run Code Online (Sandbox Code Playgroud)

但你最好先尝试一下:

for f in *.pdf 
do 
   echo mv "$f" "${f//[^0-9]/}.pdf"
done
Run Code Online (Sandbox Code Playgroud)

请注意,abc4.pdf和zzz4.pdf都将重命名为4.pdf.所以也许你使用mv -i而不仅仅是mv.

updte:解释:

我猜第一部分是清楚的; *.pdf被称为globbing,并匹配所有文件,以.pdf结尾.for f in ...只是迭代它们,每次都将f设置为其中一个.

for f in *.pdf 
do 
   mv "$f" "${f//[^0-9]/}.pdf"
done
Run Code Online (Sandbox Code Playgroud)

我猜

mv source target 
Run Code Online (Sandbox Code Playgroud)

也很清楚.如果文件名为"未命名的File1",则需要用引号将其掩盖,否则mv将读取

mv Unnamed File1 1.pdf 
Run Code Online (Sandbox Code Playgroud)

这意味着它有多个要移动的文件,Unnamed和File1,并将1.pdf解释为将两个文件移动到的目录.

好吧,我想真正的问题在这里:

"${f//[^0-9]/}.pdf"
Run Code Online (Sandbox Code Playgroud)

字符外部粘合.我们来吧

 foo=bar
Run Code Online (Sandbox Code Playgroud)

一些变量赋值然后

 $foo
 ${foo}
 "$foo"
 "${foo}"
Run Code Online (Sandbox Code Playgroud)

是四种合法的方式来引用它们.最后两个用于掩盖空白等,所以这在某些情况下没有区别,在某些情况下它是.

如果我们把东西粘在一起

 $foo4
 ${foo}4
 "$foo"4
 "${foo}"4
Run Code Online (Sandbox Code Playgroud)

第一个表单不起作用 - shell将查找变量foo4.所有其他3个表达式引用bar4 - 首先$ foo被解释为bar,然后附加4.对于某些角色,不需要屏蔽:

 $foo/fool
 ${foo}/fool
 "$foo"/fool
 "${foo}"/fool 
Run Code Online (Sandbox Code Playgroud)

将以同样的方式解释.所以无论"$ {f // [^ 0-9] /}"是什么,"$ {f // [^ 0-9] /}.pdf"都附加了".pdf".

我们接近所有mysterias的内核:

${f//[^0-9]/}
Run Code Online (Sandbox Code Playgroud)

这是表单的替换表达式

${variable//pattern/replacement}
Run Code Online (Sandbox Code Playgroud)
  • 变量是$ f(我们可以省略这里的大括号里面的$)从上面说是$ f.那很简单!
  • 替换是空的 - 这更容易.
  • 但是[^ 0-9]真的很复杂,不是吗?

-

[0-9] 
Run Code Online (Sandbox Code Playgroud)

只是从0到9的所有数字的组,其他组可以是:

[0-4] digits below 5
[02468] even digits
[a-z] lower case letters 
[a-zA-Z] all (common latin) characters 
[;:,/] semicolon, colon, comma, slash
Run Code Online (Sandbox Code Playgroud)

前面的Caret ^作为第一个角色是对团体的否定:

[^0-9] 
Run Code Online (Sandbox Code Playgroud)

表示除0到9之外的所有内容(包括点,逗号,冒号,...)都在组中.一起:

 ${f//[^0-9]/}
Run Code Online (Sandbox Code Playgroud)

从$ f中删除所有非数字,和

"${f//[^0-9]/}.pdf"
Run Code Online (Sandbox Code Playgroud)

追加.pdf - 掩盖了整个事物.

 ${v//p/r}
Run Code Online (Sandbox Code Playgroud)

和它的朋友(有许多有用的)man bash在本章中有解释Parameter Expansion.对于小组,我没有进一步阅读的来源.

  • +1不会向他们扔'sed`和'awk`. (2认同)