Suppression de fichiers spécifiques basés sur le nom de fichier du terminal

13

J'ai un répertoire contenant des fichiers avec des noms

rho_0.txt
rho_5000.txt
rho_10000.txt
rho_150000.txt
rho_200000.txt

etc. Je voudrais supprimer tous ceux qui sont un multiple de 5000.

J'ai essayé ce qui suit:, printf 'rho_%d.txt\n' $(seq 5000 10000 25000) | rmmais cela m'a donné la réponse rm: missing operand.

Y a-t-il une autre façon de procéder?

BillyJean
la source
6
Quelle que soit la façon dont vous procédez, je recommande (par sécurité) de déplacer les fichiers souhaités dans un répertoire, puis lorsque vous avez confirmé que tous et seulement les fichiers à supprimer se trouvent dans le répertoire, supprimez le répertoire.
user117529
La sécurité est importante ici. Je teste généralement ces ces choses avec d' lsabord.
Scot

Réponses:

49

Vous n'avez pas besoin d'une boucle ou de commandes supplémentaires là où vous en avez Bash Shell Brace Expansion.

rm -f rho_{0..200000..5000}.txt

Explication : {start..end..step}. L' -finvite à ignorer sur les fichiers inexistants.


Ps Pour garder la sécurité et vérifier quels fichiers seront supprimés, veuillez d'abord faire un test avec:

ls -1 rho_{0..200000..5000}.txt
αғsнιη
la source
13

rmne lit pas depuis l'entrée standard. Vous pourriez faire:

for i in $(seq 5000 5000 25000); do
    rm -i rho_${i}.txt
done

J'inclus l' -ioption de rmdemander avant la suppression afin que vous puissiez vérifier le comportement. Une fois que vous êtes sûr qu'il fait ce que vous voulez, vous pouvez omettre cette option.

Edit: Alternativement, vous pouvez faire:

for ((i = 5000; i <= 25000; i += 5000)); do
    rm -i rho_${i}.txt
done

Ce formulaire peut être plus familier si vous avez fait de la programmation.

Andy Dalton
la source
12

Vous ne pouvez pas diriger vers un programme comme si le contenu du canal était des arguments. Il est envoyé via stdin.

Vous devez utiliser xarg à cet effet:

printf 'rho_%d.txt\n' $(seq 5000 10000 25000) | xargs rm 

mais vous pouvez d'abord essayer avec écho pour voir si tout est comme vous le souhaitez:

printf 'rho_%d.txt\n' $(seq 5000 10000 25000) | xargs echo
M4rty
la source
Si votre version de seqpossède l' option -f/ --format, vous pouvez l'utiliser à la place de cette solution de contournement avec printfet substitution de commande.
David Foerster
Merci, je viens de répondre en utilisant la commande utilisée dans la question et en essayant d'expliquer son erreur rm
M4rty
9

Quelqu'un me corrige si je me trompe, mais si tous les fichiers commençant par rho_sont de cette forme, n'est-ce pas équivalent à faire

rm rho_0.txt rho_*[05]000.txt

Puisqu'un nombre (autre que 0) est un multiple de 5000 si et seulement s'il se termine en 0000 ou 5000.

(0 est un cas particulier, car il s'agit d'un multiple de 5000, mais il est généralement écrit sans zéros non significatifs supplémentaires. Si vous n'aviez pas l'intention d'inclure 0, supprimez-le de la ligne ci-dessus.)

Bien sûr, cela ne doit être utilisé que si tous les rho_*.txtfichiers de votre répertoire ont la forme souhaitée. Ne l'utilisez pas si votre répertoire contient également rho_please_dont_delete_me_5000.txt.

(Note mathématique: cela fonctionne précisément parce que tous les facteurs premiers de 5000, à savoir 2 et 5, sont également des facteurs premiers de la base dans laquelle nous travaillons, 10. De manière équivalente, il y a une puissance suffisamment grande de 10 (à savoir 10000) qui est divisible par 5000. Il n'y a pas d'astuce similaire pour faire correspondre tous ceux qui sont des multiples de 3000.)

Nate Eldredge
la source
C'est en fait la meilleure réponse.
cesarv