How to batch rename 40000 files on a folder with number count

后端 未结 2 1401
Happy的楠姐
Happy的楠姐 2021-01-24 03:27

I need to batch rename 40000 files on a folder with a number count in the end like this:. something.jpg to something_00001.jpg. I\'d like to work with the rename command, but an

相关标签:
2条回答
  • 2021-01-24 03:57

    These are powerful commands that will make lots of changes very rapidly - please test on a copy of a small subset of your data.


    Method 1 - Using "rename" (Perl tool)

    This should work with rename which you can install on macOS with:

    brew install rename
    

    The command would be:

    rename --dry-run -N "00001" 's/.jpg$/_$N.jpg/' *jpg
    

    Remove the --dry-run to actually execute the command rather than just tell you what it would do.


    Method 2 - Using GNU Parallel

    Alternatively, this should work with GNU Parallel which you can install on macOS with:

    brew install parallel
    

    The command would be:

    find . -name \*.jpg -print0 | parallel -0 --dry-run mv {} {.}_{#}.jpg
    

    where:

    • {} means "the current file",
    • {.} means "the current file minus extension", and
    • {#} means "the (sequential) job number"

    Remove the --dry-run to actually execute the command rather than just tell you what it would do.

    You mentioned you wanted an offset, so the following works with an offset of 3:

    find . -name \*.jpg -print0 | parallel -0  'printf -v new "%s_%05d.jpg" "{.}" $(({#}+3)); echo mv "{}" "$new"'
    

    Method 3 - No additional software required

    This should work using just standard, built-in tools:

    #!/bin/bash
    
    for f in *.jpg; do
       # Figure out new name
       printf -v new "%s_%05d.jpg" "${f%.jpg}" $((cnt+=1))
    
       echo Would rename \"$f\" as \"$new\"
       #mv "$f" "$new"
    done
    

    Remove the # in the penultimate line to actually do the rename.


    Method 4 - No additional software required

    This should work using just standard, built-in tools. Note that macOS comes with Perl installed, and this should be faster as it doesn't start a new mv process for each of 40,000 files like the previous method. Instead, Perl is started just once, it reads the null-terminated filenames passed to it by find and then executes a library call for each:

    find . -name \*.jpg -print0 | perl -0 -e 'while(<>){ ($sthg=$_)=~s/.jpg//; $new=sprintf("%s_%05d.jpg",$sthg,++$cnt); printf("Rename $_ as $new\n"); }'
    

    If that looks correct, change the last line so it actually does the rename rather than just telling you what it would do:

    find . -name \*.jpg -print0 | perl -0 -e 'while(<>){ ($sthg=$_)=~s/.jpg//; $new=sprintf("%s_%05d.jpg",$sthg,++$cnt); mv $_, $new; }'
    
    0 讨论(0)
  • 2021-01-24 03:58

    Here's a solution using renamer.

    $ tree
    .
    ├── beach.jpg
    ├── sky.jpg
    
    $ renamer --path-element name --index-format %05d --find /$/ --replace _{{index}} *
    
    $ tree
    .
    ├── beach_00001.jpg
    ├── sky_00002.jpg
    
    0 讨论(0)
提交回复
热议问题