Question: I have many hundreds of thousands of files in a directory. These files are named as follows: 

```
left-00001.tiff
left-00002.tiff
...
left-99999.tiff
left-100000.tiff
...
left-245000.tiff

```

I would like to rename the files as follows: 

```
left-000001.tiff
...
left-099999.tiff
...
left-245000.tiff

```

I found elegant solution to this problem [here](https://stackoverflow.com/questions/5417979/batch-rename-sequential-files-by-padding-with-zeroes).

This solution implements a bash script called `zeropad.sh`. the bash is coded as follows:

```
#!/bin/bash
num=`expr match "$1" '[^0-9]*\([0-9]\+\).*'`
paddednum=`printf "%06d" $num`
echo ${1/$num/$paddednum}

```

and can be applied iteratively using `for loop` as follows:

```
for i in *.tiff;do mv $i `./zeropad.sh $i`; done

```

However, this solution takes a very long time because it does much unnecessary work renaming all the files which are already properly padded. `i.e. as %06d type numbers`. For my own purposes this is solution is very slow. 

I have two questions: 

1- How can I modify the iterator to only apply `zeropad.sh` on files which need to be zero padded? 

2- How can I use the command `touch` in a `for loop` to generate test data? It is crucial to verify that this script works before I apply it on the original data.

Answer: 
What's costly is to fork so many processes and run so many commands for each file.

With `zsh`:

```
zmodload zsh/files # make mv builtin to speed things up
autoload zmv
zmv -n '(*-)(<->)(.tiff)' '$1${(l:6::0:)2}$3'

```

(remove `-n` when happy)

That's all with builtins, so doesn't fork any process nor execute any file.

Or with `perl`'s `rename`:

```
rename -n 's/\d+(?=\.tiff\z)/sprintf "%06d", $&/e' ./*[0-9].tiff

```
I love Perl one-liners:

```
ls left-*.tiff | perl -ne 'if(m/(\S+)-(\d+).tiff/){chomp;printf "mv $_ left-%06d.tiff\n", $2}' | bash

```

PS, make sure to double check the output before piping into `bash`. Just to be safe.