How to rename files with ordering using Bash {thisfile.jpg -> newfile1.jpg, thatfile.jpg -> newfile2.jpg}

StackOverflow https://stackoverflow.com/questions/20382612

  •  29-08-2022
  •  | 
  •  

Frage

Let's say I have 100 jpg files.

DSC_0001.jpg
DSC_0002.jpg
DSC_0003.jpg
....
DSC_0100.jpg

And I want to rename them like

summer_trip_1.jpg
summer_trip_2.jpg
summer_trip_3.jpg
.....
summer_trip_100.jpg    

So I want these properties to be modified: 1. filename 2. order of the file(as the order by date files were created)

How could I achieve this by using bash? Like:

for file in *.jpg ; do mv blah blah blah ; done

Thank you!

War es hilfreich?

Lösung

It's very simple: have a variable and increment it at each step.

Example:

cur_number=1
prefix="summer_trip_"
suffix=""
for file in *.jpg ; do
    echo mv "$file" "${prefix}${cur_number}${suffix}.jpg" ;
    let cur_number=$cur_number+1  # or :  cur_number=$(( $cur_number + 1 ))
done

and once you think it's ready, take out the echo to let the mv occur.

If you prefer them to be ordered by file date (usefull, for example, when mixing photos from several cameras, of if on yours the "numbers" rolled over):

change

for file in *.jpg ; do

into

for file in $( ls -1t *.jpg ) ; do

Note that that second example will only work if your original filenames don't have space (and other weird characters) in them, which is fine with almost all cameras I know about.

Finally, instead of ${cur_number} you could use $(printf '%04s' "${cur_number}") so that the new number has leading zeros, making sorting much easier.

Andere Tipps

How about using rename ?

 rename DSC_ summer_trip_ *.jpg

See man page of rename

This works if your original numbers are all padded with zeroes to the same length:

i=0; for f in DSC_*.jpg; do mv "$f" "summer_trip_$((++i)).jpg"; done 

If I understand your goal correctly:

So I want these properties to be modified: 1. filename 2. order of the file(as the order by date files were created)

if numbers of renamed files shall increment in order by file creation date, then use the following for loop:

for file in $(ls -t -r *.jpg); do

-t sorts by mtime (last modification time, not exactly creation time, newest first) and -r reverses the order listing oldest first. Just in case if original .jpg file numbers are not in the same order as pictures were taken. As it was mentioned previously, this won't work if file names have whitespaces. If your files have spaces please try modifying IFS variable before for loop:

IFS=$'\n'

It will force split of 'ls' command results on newlines only (not whitespaces). Also it would fail if there is a newline in a file name (rather exotic IMHO :). Changing IFS may have some subtle effects further in your script, so you can save old one and restore after the loop.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top