重命名文件以向数字添加前导零

重命名文件以向数字添加前导零

我已经尝试了一堆重命名命令的示例,但我无法弄清楚执行我想要的操作的语法。

我有一堆标有类似内容的文件

File_Ex_1.jpg
File_Ex_2.jpg
File_Ex_3.jpg
File_Ex_4.jpg
...
File_Ex_10.jpg
File_Ex_11.jpg
etc. 

我只想通过插入来更改其中一些,0以便文件名具有相同的字符数。

所以我File_Ex_1.jpg想去File_Ex_01.jpgFile_Ex_2.jpgFile_Ex_02.jpg

如何使用重命名命令来执行此操作?

rename命令是通过安装的自制在 Mac 上。输出rename -v

rename -v
Usage:
    rename [switches|transforms] [files]

    Switches:

    -0/--null (when reading from STDIN)
    -f/--force or -i/--interactive (proceed or prompt when overwriting)
Wide character in print at /System/Library/Perl/5.18/Pod/Text.pm line 286.

    -g/--glob (expand "*" etc. in filenames, useful in Windows™ CMD.EXE)
    -k/--backwards/--reverse-order
    -l/--symlink or -L/--hardlink
    -M/--use=*Module*
    -n/--just-print/--dry-run
    -N/--counter-format
    -p/--mkpath/--make-dirs
    --stdin/--no-stdin
    -t/--sort-time
    -T/--transcode=*encoding*
    -v/--verbose

    Transforms, applied sequentially:

    -a/--append=*str*
    -A/--prepend=*str*
    -c/--lower-case
    -C/--upper-case
    -d/--delete=*str*
    -D/--delete-all=*str*
    -e/--expr=*code*
    -P/--pipe=*cmd*
    -s/--subst *from* *to*
    -S/--subst-all *from* *to*
    -x/--remove-extension
    -X/--keep-extension
    -z/--sanitize
    --camelcase --urlesc --nows --rews --noctrl --nometa --trim (see manual)

答案1

尝试用这个:

rename -e 's/\d+/sprintf("%02d",$&)/e' -- *.jpg

例子:

$ ls
Device_Ex_10.jpg  Device_Ex_1.jpg  Device_Ex_4.jpg  Device_Ex_7.jpg
Device_Ex_11.jpg  Device_Ex_2.jpg  Device_Ex_5.jpg  Device_Ex_8.jpg
Device_Ex_12.jpg  Device_Ex_3.jpg  Device_Ex_6.jpg  Device_Ex_9.jpg
$ rename -e 's/\d+/sprintf("%02d",$&)/e' -- *.jpg
$ ls
Device_Ex_01.jpg  Device_Ex_04.jpg  Device_Ex_07.jpg  Device_Ex_10.jpg
Device_Ex_02.jpg  Device_Ex_05.jpg  Device_Ex_08.jpg  Device_Ex_11.jpg
Device_Ex_03.jpg  Device_Ex_06.jpg  Device_Ex_09.jpg  Device_Ex_12.jpg

我从这里获取了参考: https://stackoverflow.com/questions/5417979/batch-rename-sequential-files-by-padding-with-zeroes

这里适应您的特定rename实施。

答案2

使用您似乎正在使用的 rename 版本,以下表达式应该执行您请求的转换(示例包含名为 的文件的目录File_Ex_{1..11}.jpg):

$ rename -n -e 's/_(\d\.)/_0$1/g' -- *.jpg
'File_Ex_1.jpg' would be renamed to 'File_Ex_01.jpg'
'File_Ex_2.jpg' would be renamed to 'File_Ex_02.jpg'
'File_Ex_3.jpg' would be renamed to 'File_Ex_03.jpg'
'File_Ex_4.jpg' would be renamed to 'File_Ex_04.jpg'
'File_Ex_5.jpg' would be renamed to 'File_Ex_05.jpg'
'File_Ex_6.jpg' would be renamed to 'File_Ex_06.jpg'
'File_Ex_7.jpg' would be renamed to 'File_Ex_07.jpg'
'File_Ex_8.jpg' would be renamed to 'File_Ex_08.jpg'
'File_Ex_9.jpg' would be renamed to 'File_Ex_09.jpg'

(删除标志-n以实际进行重命名。)

的参数-e是 Perl 搜索和替换表达式;其中 _(\d\.)匹配 am 下划线,后跟一个数字,然后是一个点,并将下划线替换为_0,从而插入前导零。$1是对括号内的组(数字和点)的反向引用,并在新文件名中保持不变。

答案3

虽然可以通过prename命令完成,但我想提供一个 python 替代方案:

$ ls
File_Ex_1.jpg  File_Ex_2.jpg  File_Ex_3.jpg  File_Ex_4.jpg

$ ./pad_zeros.py *                                                                                                       

$ ls
File_Ex_01.jpg  File_Ex_02.jpg  File_Ex_03.jpg  File_Ex_04.jpg  pad_zeros.py*

脚本pad_zeros.py很简单:

#!/usr/bin/env python
import sys,os,re

for file in sys.argv[1:]:
    if __file__ in file: continue
    words = re.split('_|\.',file)
    words[-2] = words[-2].zfill(2)
    new_name = "_".join(words[:-1]) + "." + words[-1]
    os.rename(file,new_name)

它在命令行上获取参数,迭代它们,并使用.zfill()命令填充零(在本例中为两个字符)。由于我们对同一文件夹中的所有文件进行操作,因此可以使用 glob-star。

答案4

上面的一个答案给出了:

rename -e 's/\d+/sprintf("%02d",$&)/e' -- *.jpg

然而,这给了我不正确的结果,因为 *.jpg 按严格的数字顺序对文件进行排序。rename带着旗帜进行-n预演会给我带来:

rename(9999.jpg, frames_0000039996.jpg) 
rename(999.jpg, frames_0000039997.jpg) 
rename(99.jpg, frames_0000039998.jpg) 
rename(9.jpg, frames_0000039999.jpg)

可以通过以下方式获得正确的结果:

rename 's/.+/our $i; sprintf("frames_%010d.jpg", 0+$i++)/e' $(ls -1 | sort -V)

这使

rename(9999.jpg, frames_0000039996.jpg)
rename(999.jpg, frames_0000039997.jpg)
rename(99.jpg, frames_0000039998.jpg)
rename(9.jpg, frames_0000039999.jpg)

-n旗帜。

相关内容