sorting numériquement des noms de files lorsqu'ils ont un préfixe non numérique

J'ai des files au format suivant: x1 x2 ... x10 x11 ... x101 ...

Je veux renommer ces files, donc ils ont tous la même longueur de nom: x001 x002 ... x010 ...

Je peux le faire avec des files qui n'ont pas le préfixe non-numérique (en utilisant simplement sort -n suivi d'un while read x; ), mais sort ne reconnaît pas la valeur numérique, quand il n'est pas au début de la nom de file.

Vous pouvez essayer de sortinger les files en utilisant l'option v (version) de ls eg ls -1v . Ou vous pouvez utiliser le sorting numérique avec x comme délimiteur: ls | sort -n -t 'x' +1 ls | sort -n -t 'x' +1

Mais vous ne devez pas sortinger les files pour les renommer. Vous pouvez simplement regarder la longueur du nom du file et le remplir avec des zéros si nécessaire. Voici un petit script qui fait ça:

 prefix=x maxLength=4 for file in ${prefix}* do if [ ${#file} -lt $maxLength ] then newFile=$file while [ ${#newFile} -lt $maxLength ] do newFile=${newFile/$prefix/${prefix}0} done mv $file $newFile fi done 

Êtes-vous sûr de devoir les sortinger en premier?

 m=0 for f in x*; do [ "${#f}" -gt "$m" ] && m=${#f} done for f in x*; do echo mv -- "$f" "${f%${f#?}}$( printf '%0.*d' $(( m - 1 )) "${f#?}" )" done 

Si votre implémentation printf ne prend pas en charge la syntaxe ci-dessus, utilisez printf "%0.$(( m - 1 ))d" "${f#?}" .

Supprimer l'écho lorsqu'il est satisfait.

Juste pour développer la réponse de dogbane, sort a une option de sorting des versions. Notez que certaines plates-forms (par exemple busybox) n'ont pas cette option.

Vous pouvez l'utiliser comme ceci:

 sort -V sort --version-sort 

Ou à la version sortinger la nième colonne:

 sort -knV 

Vous avez besoin de renommer, alors qu'il existe des outils similaires, qui pourraient vous servir aussi:

 touch x1 x2 x10 x11 x101 ls ; rename 's/x/x0/' x[0-9] 

x1 x10 x101 x11 x2

 ls ; rename 's/x/x0/' x[0-9][0-9] 

x01 x02 x10 x101 x11

 ls 

x001 x002 x010 x011 x101

'rename' fait partie de certains packages perl, si vous devez l'installer, au less disponible pour Linux.

Sans renommer, il existe une solution similaire avec une boucle:

 rm * touch x1 x2 x10 x11 x101 for f in x[0-9] ; do mv $f ${f/x/x0}; done for f in x[0-9][0-9] ; do mv $f ${f/x/x0}; done ; ls 

x001 x002 x010 x011 x101