187 votes

Déplacer tous les fichiers sauf un

Comment puis-je déplacer tous les fichiers sauf un ? Je cherche quelque chose comme :

'mv ~/Linux/Old/!Tux.png ~/Linux/New/'

où je déplace les vieilles choses vers les nouvelles - sauf le dossier Tux.png . Le signe !- représente une négation. Existe-t-il un outil pour ce travail ?

168voto

sth Points 91594

Si vous utilisez bash et avez l'option extglob (ce qui est généralement le cas) :

mv ~/Linux/Old/!(Tux.png) ~/Linux/New/

1 votes

J'ai eu un problème lorsque j'ai testé la commande pour plusieurs éléments : mv ~/Linux/Old/ !(Tux.png Tux1.png Tux2.png) ~/Linux/New/ Il vide tout le répertoire Old. Quel est le problème ?

10 votes

@UnixBasics, essaie : ~/Linux/Old/ !(Tux.png|Tux1.png|Tux2.png)

0 votes

@Juliano Commande très cool ! Y a-t-il d'autres opérations mathématiques comme OR et XOR ? Je suppose qu'un pipe est pour AND.

115voto

Masi Points 22232

Mettez ce qui suit dans votre .bashrc

shopt -s extglob

Il étend les regex. Vous pouvez alors déplacer tous les fichiers sauf un par

mv !(fileOne) ~/path/newFolder

Exceptions par rapport à d'autres commandements

Notez que, lors de la copie de répertoires, le forward-flash ne peut pas être utilisé dans le nom comme remarqué dans le fil de discussion Pourquoi extglob sauf rupture de condition ? :

cp -r !(Backups.backupdb) /home/masi/Documents/

donc Backups.backupdb/ est erroné ici avant la négation et je ne l'utiliserais pas non plus pour déplacer des répertoires à cause du risque d'utilisation erronée de globs avec d'autres commandes et d'autres exceptions possibles.

3 votes

C'est en fait la bonne réponse. La mienne était complètement fausse ; heureusement, je l'avais utilisée dans un dossier ne contenant que quelques fichiers. Voici plus d'informations sur la méthode présentée par Masi : wiki.bash-hackers.org/syntaxe/modèle Allez sur "Extended pattern language" et vous trouverez plus d'informations à ce sujet. Merci à @paul-whittaker d'avoir signalé ce problème.

0 votes

Il s'agit d'une ancienne réponse mais elle est toujours valable. J'utilise Ubuntu 18 et extglob semble être activé par défaut (je ne l'ai pas acheté). J'ai utilisé la commande suivante pour déplacer tous les fichiers du répertoire actuel dans une archive qui se trouve également dans ce répertoire, sans inclure aucun autre dossier d'archive : mv !(arc*) archive_190629b

78voto

J'opterais pour la méthode traditionnelle find & xargs :

find ~/Linux/Old -maxdepth 1 -mindepth 1 -not -name Tux.png -print0 | 
    xargs -0 mv -t ~/Linux/New

-maxdepth 1 fait en sorte que la recherche ne soit pas récursive. Si vous ne vous intéressez qu'aux fichiers, vous pouvez dire -type f . -mindepth 1 fait qu'il n'inclut pas le ~/Linux/Old le chemin lui-même dans le résultat. Fonctionne avec n'importe quel nom de fichier, y compris ceux qui contiennent des nouvelles lignes intégrées.

Un commentaire note que le mv -t est probablement une extension GNU. Pour les systèmes qui ne l'ont pas

find ~/Linux/Old -maxdepth 1 -mindepth 1 -not -name Tux.png \
    -exec mv '{}' ~/Linux/New \;

1 votes

Upvoted car il encourage l'apprentissage d'un outil puissant, trouver. Attention, pour les fichiers avec des espaces, cela ne fonctionnera pas. Considérez "find -print0 | xargs -0" ou bien renoncez à xargs : "find [ce que vous avez dit] -exec mv -t {} ~/Linux/New \ ;"

1 votes

Si votre commande mv n'a pas l'option -t, alors utilisez soit "find ... -exec mv {} Linux/New \ ;" ou "find ... | xargs -I {} mv {} Linux/Nouveau". L'option -t semble être une extension GNU, ce qui est bien pour Linux, mais probablement pas ailleurs.

0 votes

Jhs, oh j'ai échoué. je pensais que xargs se séparait aux nouvelles lignes mais pas aux espaces. il semble que j'ai confondu avec "read" :) je vais corriger cela.

17voto

Juliano Points 13802

Pour bash, répondre à qqch. est correcte. Voici le zsh (mon shell de choix) syntaxe :

mv ~/Linux/Old/^Tux.png ~/Linux/New/

Nécessite EXTENDED_GLOB option du shell à définir.

4 votes

Que faire si l'on veut exclure deux fichiers ?

15voto

alex.pilon Points 169

Je trouve que c'est un peu plus sûr et plus facile à utiliser pour les déplacements simples qui excluent certains fichiers ou répertoires.

ls -1 | grep -v ^$EXCLUDE | xargs -I{} mv {} $TARGET

0 votes

C'est la meilleure solution pour Busybox / ASH

1 votes

Cela a fonctionné pour moi dans une situation où j'ai dû déplacer tous les fichiers, sauf quelques dossiers, vers un autre répertoire.

0 votes

El -l option pour ls inclura beaucoup d'informations non pertinentes sur la ligne de commande et entraînera l'échec de la commande mv.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X