Je me rends compte que toute question demandant comment supprimer des fichiers doit être prise avec beaucoup de soin. Ma première réponse a été trop hâtive, je n'ai pas pris le fait que la liste de fichiers pouvait être mal formée pour être utilisée avec egrep. J'ai édité la réponse pour réduire ce risque.
Cela devrait fonctionner pour les fichiers qui n'ont pas d'espace dans le nom:
Reconstruisez d'abord votre liste de fichiers pour être sûr de correspondre au nom de fichier exact:
sed -e 's,^,^,' -e 's,$,$,' filelist > newfilelist
construire les commandes rm
cd your_directory
ls | egrep -vf newfilelist | xargs -n 1 echo rm > rmscript
Vérifiez si le script rm vous convient (vous pouvez le faire avec "vim" ou "less").
Effectuez ensuite l'action:
sh -x rmscript
Si les fichiers ont des espaces dans leur nom (si les fichiers ont le "
dans le nom, cela ne fonctionnera pas):
ls | egrep -vf newfilelist | sed 's,^\(.*\)$,rm "\1",' > rmscript
bien sûr, la liste de fichiers ne doit pas se trouver dans le même répertoire!
ÉDITÉ:
La liste des fichiers de Nathan contenait des noms qui correspondaient à tous les fichiers du répertoire (comme "html" correspond à "bob.html"). Donc rien n'a été supprimé car egrep -vf
absorbé tout le flux. J'ai ajouté une commande pour mettre un "^" et un "$" autour de chaque nom de fichier. J'ai eu de la chance ici que la liste de fichiers de Nathan soit correcte. Aurait-il été formaté DOS avec des lignes terminées CR-LF ou avec des espaces supplémentaires, aucun fichier n'aurait été conservé par l'egrep et tout aurait été supprimé.
ls
fournit les noms de fichiers du répertoire,egrep -vf filelist
filtrez vos 50 noms de fichiers. J'ai bien peur que vous ayez supprimé tous vos fichiers.Préconstruisez les arguments pour
find
:Utilisez les
echo
pièces pour voir ce qui serait construit. Retirez lesecho
pièces pour le faire fonctionner.Mise à jour: Démonstration:
la source
'
) devraient être ajoutés, c'estkeep=( -name \'"$REPLY"\' )
-à- dire etkeep+=( -o -name \'"$REPLY"\' )
.Avec
zsh
:Il lit les lignes d'
filelist
un tableau et utilise ensuite les qualificatifs glob /e
chaîne pour glob / sélectionner uniquement les noms de fichiers non présents dans le tableau: le.
sélectionne uniquement les fichiers normaux (ajoutezD
si votre liste contient des fichiers de points) et le négatif annule en^e_'expression'_
outre ne sélectionne que ceux pour dont l'expression renvoie false, c'est-à-dire si leur nom ($REPLY
) n'est pas un élément du tableau .Si vous êtes satisfait du résultat, remplacez
print -rl
parrm
pour supprimer réellement les fichiers:Pour sélectionner et supprimer des fichiers de manière récursive, utilisez le modificateur
*/**
glob with${REPLY:t}
glob:la source
Si vous mettez le contenu du répertoire dans un fichier comme ceci:
Ouvrez la liste de fichiers avec un éditeur de texte et supprimez tous les fichiers sauf ceux que vous souhaitez supprimer . C'est en gras car c'est l'approche opposée à la réponse ci-dessus
Essaye ça:
Si vous voyez votre liste de fichiers sortie à l'écran, remplacez echo par
rm -v
, comme ceci:la source
Exécutez le script ci-dessous.
all_files
.not_to_be_deleted_files
).not_to_be_deleted_files
etfiles_to_be_deleted
à la finnot_to_be_deleted_files
car nous avons besoin de ces 2 fichiers.join
commande linux et en redirigeant la sortie vers lefiles_to_be_deleted
fichier.files_to_be_deleted
et je supprime les fichiers mentionnés dans ce nom de fichier.Le script est comme ci-dessous.
PS : Probablement, si vous souhaitez que cela soit enregistré en tant que script et l'exécutez, vous pouvez également ajouter le nom du script en utilisant
echo scriptname >> not_to_be_deleted_files
.Bien que ce ne soit pas obligatoire, je préfère le faire car il n'y aura aucun regret plus tard. J'ai testé un petit ensemble de fichiers et cela a fonctionné dans mon système. Cependant, si vous voulez en être sûr, essayez d'abord dans un
test
répertoire, puis supprimez les fichiers dans le répertoire d'origine.la source
la source
J'ai opté pour une approche plus sûre et beaucoup plus rapide car j'avais 18 000 fichiers dans la liste! J'avais besoin de nettoyer des images dans une grande installation Drupal.
La suppression de tous les fichiers qui ne figurent pas dans la liste revient à ne conserver que ceux qui figurent dans la liste. J'ai donc décidé de copier les fichiers de la liste vers un autre emplacement, mais copier 20 Go de fichiers prendrait trop de place et serait très lent également. L'astuce consiste donc à copier les fichiers sous
hardlinks
, à la place, en utilisant l'-l
option decp
. Cela ne prend presque pas de place et est très rapide. De plus, comme j'avais besoin de conserver la structure du répertoire, j'ai utilisé l'--parents
option.Voici un extrait de ma liste de fichiers:
Ainsi, un exemple de ligne serait, avec temp étant la destination:
Cela va créer cette structure:
Notez que la destination doit être dans le même système de fichiers que la source pour que les liens physiques fonctionnent.
L'étape suivante consiste à construire le script:
Maintenant, en supposant que vous avez déjà créé le répertoire vide / certains / où / temp, vous pouvez copier les fichiers comme ceci:
Notez comment les erreurs se terminent
missing_files
. Le bonus supplémentaire de cette approche est que vous obtiendrez une liste de fichiers de la liste d'origine qui n'existent pas !Après avoir exécuté le script, temp ne contiendra que les fichiers qui se trouvent dans la liste des fichiers, mais sans rien supprimer et sans prendre d'espace supplémentaire. Si vous êtes satisfait du résultat, vous pouvez supprimer tous les fichiers originaux, y compris les sous-dossiers.
Enfin, déplacez les fichiers et dossiers de temp vers leur emplacement d'origine.
Pour les 18 000 fichiers, cela n'a pris que quelques secondes.
la source
Sûr, simple.
cd
dans le répertoire.Créez un répertoire temporaire.
terminé.
la source