web-dev-qa-db-fra.com

Répertorie les fichiers en affichant uniquement le chemin d'accès complet et la taille du fichier à partir de l'invite de commande Windows

J'essaie de générer un fichier texte contenant le nom du fichier (y compris le chemin d'accès complet) et la taille du fichier pour tous les fichiers d'un répertoire particulier et l'un de ses sous-répertoires (c'est-à-dire récursivement). Idéalement, je ne veux pas de virgules dans la taille du fichier (mais je me contenterai d'eux!)

La commande suivante le fait mais sans la taille du fichier:

dir /b /s /a:-D > results.txt

Un exemple de sortie ressemblerait à ceci:

C:\Users\Martin\Pictures\Table\original\PC120013.JPG  227298
C:\Users\Martin\Pictures\Table\original\PC120014.JPG  123234
C:\Users\Martin\Pictures\Table\original\PC120015.JPG  932344

Je ne pense pas que cela soit possible en utilisant dir seul, bien que j'aimerais beaucoup avoir tort. Y a-t-il un autre moyen de faire cela en utilisant uniquement les commandes disponibles à partir de l'invite de commandes?

48
Martin Wilson

Cela devrait le faire:

@echo off & for /f %a in ('dir /s /b') do echo %~fa %~za

Ce n'est pas très efficace ... son utilisation pour des dossiers contenant une tonne de fichiers peut être fragmentaire, essayez donc d'abord sur de petits dossiers.

Du "pour /?" texte d'aide (j'ai utilisé 'a' au lieu de 'je')

In addition, substitution of FOR variable references has been enhanced.
You can now use the following optional syntax:

%~I         - expands %I removing any surrounding quotes (")
%~fI        - expands %I to a fully qualified path name
%~dI        - expands %I to a drive letter only
%~pI        - expands %I to a path only
%~nI        - expands %I to a file name only
%~xI        - expands %I to a file extension only
%~sI        - expanded path contains short names only
%~aI        - expands %I to file attributes of file
%~tI        - expands %I to date/time of file
%~zI        - expands %I to size of file
%~$PATH:I   - searches the directories listed in the PATH
               environment variable and expands %I to the
               fully qualified name of the first one found.
               If the environment variable name is not
               defined or the file is not found by the
               search, then this modifier expands to the
               empty string

The modifiers can be combined to get compound results:

%~dpI       - expands %I to a drive letter and path only
%~nxI       - expands %I to a file name and extension only
%~fsI       - expands %I to a full path name with short names only
%~dp$PATH:I - searches the directories listed in the PATH
               environment variable for %I and expands to the
               drive letter and path of the first one found.
%~ftzaI     - expands %I to a DIR like output line
27
Brian Adkins

Alternative n ° 1: FOR/R est plus intuitif que n ° 2 pour moi.
Alternative n ° 2: FOR/F corrige le problème des "espaces dans les noms" dans la suggestion de BrianAdkins.
Variante n ° 3: FORFILES serait mon choix, sauf que le chemin est entre guillemets.

Brian ou d’autres gourous ont peut-être une solution plus élégante ou peuvent suggérer une douzaine d’autres solutions, mais ces trois solutions fonctionnent. J'ai essayé d'utiliser FOR TOKENS, mais j'ai ensuite dû supprimer les en-têtes et les pieds de page; je suis donc revenu au premier rang. J'ai également envisagé de créer un petit fichier .bat et de l'appeler, mais cela ajoute un autre fichier (bien qu'il offre une plus grande flexibilité, comme le ferait une fonction).

J'ai testé toutes les alternatives avec répertoire et noms de fichier avec espaces incorporés, un nom de fichier de plus de 200 caractères, un nom de fichier sans extension et la racine d'un petit lecteur (juste pour le temps; un peu lent - tout comme Brian l'a suggéré - mais alors cherche dans l'Explorateur Windows, c'est pourquoi j'ai installé l'application de recherche Everything).

Alternative # 1: FOR/R

Best (?) Tout en essayant de comprendre pourquoi la solution de Brian ne fonctionnait pas pour moi, j'ai examiné HELP FOR et j'ai décidé d'essayer l'approche/R. (La création d'un fichier serait la même que dans la variante 2.)

@echo off & for /R "c:\deletelater\folder with spaces" %A in (*.*) do echo %~fA %~zA

Exemple - Fonctionne (répertoire différent de celui indiqué ci-dessus pour illustrer la récursivité)

@echo off & for /R "c:\deletelater" %A in (*.*) do echo %~fA %~zA
c:\DeleteLater\Name with Spaces.txt 19800676
c:\DeleteLater\NoSpacesLongName.txt 21745440
c:\DeleteLater\Folder with Spaces\2nd Name with Spaces.txt 5805492
c:\DeleteLater\Folder with Spaces\2ndNoSpacesLongName.txt 3870322
c:\DeleteLater\FolderNoSpaces\3rd Name with Spaces.txt 27874695
c:\DeleteLater\FolderNoSpaces\3rdNoSpacesLongName.txt 28726032

Alternative n ° 2: POUR/F

BrianAdkins a suggéré: @echo off & for /f %a in ('dir /s /b') do echo %~fa %~za

A réponse corrigée est:

@echo off & for /f "delims=*" %A in ('dir /s /b') do echo %~fA %~zA 

Un plus complet answer avec les répertoires supprimés et le résultat (ajouté) à un fichier est:

@echo Results on %DATE% for %CD% >> YourDirFile.txt & echo off & for /f "delims=*" %A in ('dir /s /b /a:-d') do echo %~fA %~zA >> YourDirFile.txt

Remarque: "delims = *" spécifie un caractère non autorisé dans les noms de fichiers.
Remarque: la 2e commande supprime également les répertoires via/a: -d.
Remarque: Utilisez le nom de variable FOR en majuscule pour clarifier la distinction entre variable et paramètre de variable si quelqu'un choisit des noms de variable différents.
Remarque: ajouté au fichier uniquement pour les grimaces, car le terminal opérateur a demandé la sortie dans un fichier.

Je suppose que je devrais vraiment vérifier le statut d’ECHO et le réinitialiser également.

Issue - Espaces dans les noms

La solution proposée par Brian ne gère pas les noms de fichiers et de dossiers contenant des espaces (du moins sur ma configuration Vista).

Exemple - Wrong (Sans délimitations; inclut le répertoire de suppression par OP mais avec une taille à la fois avant et après le nom du fichier pour plus de soulignement)

Nom et taille tronqués (4 fichiers sur 6 incorrects):

@echo off & for /f %A in ('dir /s /b /a:-d') do echo %~zA %~fA %~zA
 C:\DeleteLater\Name
21745440 C:\DeleteLater\NoSpacesLongName.txt 21745440
 C:\DeleteLater\Folder
 C:\DeleteLater\Folder
 C:\DeleteLater\FolderNoSpaces\3rd
28726032 C:\DeleteLater\FolderNoSpaces\3rdNoSpacesLongName.txt 28726032

Exemple - Correct (note sortie à l'écran, non ajoutée au fichier)

@echo off & for /f "delims=*" %A in ('dir /s /b /a:-d') do echo %~fA %~zA
C:\DeleteLater\Name with Spaces.txt 19800676
C:\DeleteLater\NoSpacesLongName.txt 21745440
C:\DeleteLater\Folder with Spaces\2nd Name with Spaces.txt 5805492
C:\DeleteLater\Folder with Spaces\2ndNoSpacesLongName.txt 3870322
C:\DeleteLater\FolderNoSpaces\3rd Name with Spaces.txt 27874695
C:\DeleteLater\FolderNoSpaces\3rdNoSpacesLongName.txt 28726032

Variante n ° 3: FORFILES (Numéro de citation)

Cette solution est directement issue des deux derniers exemples de la documentation de FORFILES (forfiles /?).

FORFILES /S /M *.doc /C "cmd /c echo @fsize"
FORFILES /M *.txt /C "cmd /c if @isdir==FALSE notepad.exe @file"

La combinaison de ces exemples et l'écriture dans un fichier donne la réponse (presque):

forfiles /s  /c "cmd /c if @isdir==FALSE echo @path @fsize" >>ForfilesOut.txt

Notez que le chemin est entre guillemets dans la sortie.
Peu importe que echo on ou echo off soit basculé.
Ajouter une ligne vierge séparant chaque répertoire constituerait une extension triviale du SI.

Attention : L'utilisation du masque /m *.* ne renverra pas les fichiers sans extension (comme le dernier fichier de l'exemple)!

Aside : Ceci écrit un fichier dans chaque répertoire avec le contenu de ce répertoire uniquement:
forfiles /s /c "cmd /c if @isdir==FALSE echo @path @fsize >>ForfilesSubOut.txt" Pas ce que le PO voulait, mais parfois pratique.

Exemple - Fonctionne (mais avec le chemin complet entre guillemets)

forfiles /s  /c "cmd /c if @isdir==FALSE echo @path @fsize"

"c:\DeleteLater\Name with Spaces.txt" 19800676
"c:\DeleteLater\NoSpacesLongName.txt" 21745440
"c:\DeleteLater\Folder with Spaces\2nd Name with Spaces.txt" 5805492
"c:\DeleteLater\Folder with Spaces\2ndNoSpacesLongName.txt" 3870322
"c:\DeleteLater\FolderNoSpaces\3rd Name with Spaces.txt" 27874695
"c:\DeleteLater\FolderNoSpaces\3rdNoSpacesLongName.txt" 28726032
"c:\DeleteLater\MoreFiles\A really really long file name that goes on and on 123456789 asdfghjkl zxcvnm qwertyuiop and still A really really long file name that goes on and on 123456789 qwertyuiop and still further roughly 225 characters by now.txt" 447
"c:\DeleteLater\MoreFiles\New Text Document no extension" 0

Cet exemple inclut un répertoire supplémentaire avec un nom de fichier super long et un nom de fichier sans extension.

Issue: Chemin entre guillemets

Ainsi, existe-t-il un moyen simple de supprimer les guillemets indésirables (?) Selon l'exemple OP et de sauvegarder la variante n ° 3: FORFILES. (Question rhétorique: les citations sont-elles une fonctionnalité ou un défaut?)

14
BillR

Je réalise que cela nécessite un utilitaire supplémentaire , mais vous pouvez y parvenir assez succinctement à l'aide de l'utilitaire sfk :

sfk cwd +run -yes "sfk list -size -tab $qfile +toclip"

sfk fromclip > C:\_temp\sfk_list_output.txt

(J'ai eu l'approche en utilisant commande sfk chaînant ici )

1
rogersillito
powershell "dir | select name,length"

Cela peut être tricher sur la question des PO. Cependant, la question n'est plus pertinente sur les systèmes Windows modernes. L'alias Dir a été utilisé pour aider à établir le lien logique.

1
someguy

Je trouve la commande "du" très utile et elle fonctionne à la fois sous Windows et sous Unix (utilisée pour vérifier si tous les fichiers ont été copiés lors du transfert de nombreuses données d'un PC Windows vers un serveur Web Linux):

du -ah "C:\your_dir" > "C:\file_list.txt"

les sorties:

15  C:\your_dir/.htaccess
608 C:\your_dir/folder/hello.txt
1.0 C:\your_dir/folder/subfolder/test.txt
1.0 C:\your_dir/folder/subfolder
1.2M    C:\your_dir/folder/world.txt
1.2M    C:\your_dir/folder
9.0 C:\your_dir/no_file_ending
11  C:\your_dir/sample document 1.txt
684K    C:\your_dir/sample document 2 - äöüßÄÖÜáà.txt
1.9M    C:\your_dir

Cependant, je ne pouvais voir correctement que les caractères spéciaux dans le Bloc-notes, pas dans le Bloc-notes ++ (il doit s'agir d'un encodage ANSI/UTF-8, pas le temps d'analyser exactement maintenant). De plus, je n'ai pas trouvé de solution pour afficher la taille après le nom du fichier. Utilisez les options "b" ou "k" au lieu de "h" pour afficher la taille en octets ou en kilo-octets. J'ai eu quelques problèmes lors de l'exécution de la commande en dehors du dossier que je souhaite analyser. Il vaut donc mieux entrer la commande dans le bon répertoire ("C:\your_dir" dans cet exemple) et la spécifier dans la commande.

0
Matthias Luh

J'ai atteint ceci avec la commande suivante:

(for /R "\path\to\directory\" %A in (*.*) do echo %~fA %~zA) | findstr /v "echo"

Le résultat:

D:\Users\Natasha>(for /R ".\" %A in (*.*) do echo %~fA %~zA) | findstr /v "echo"


D:\Users\Natasha\Flowers_ (12).jpg 118886

D:\Users\Natasha\SomeFolder\data.txt 1241

D:\Users\Natasha\SomeFolder\CS\Counter-Strike_1.6.exe 272645624

P.S. Ceci est basé sur la réponse de BillR (variante n ° 1). Cependant, dans mon cas, il se bloque avec @echo off.

0
natasha

Vous trouverez ci-dessous la méthode utilisée pour localiser divers fichiers vidéo occupant trop de place sur un lecteur réseau et pour écrire les résultats dans un fichier texte sur un PC local.

Je publie ma propre réponse un peu tardive pour trois raisons. Un, j'aime les réponses concises. Deuxièmement, cette ligne de script unique fonctionnait pour moi dans plusieurs paramètres, y compris sur un réseau. Troisièmement, par commentaire potentiellement obscur de Don Vince dans la réponse de BrianAdkins, l’utilisation de jetons peut contourner les problèmes liés aux noms de fichiers contenant des espaces.

for /f "tokens=*" %%a in ('dir H:\*.mov H:\*.avi H:\*.wmv H:\*.mp4 /s /b') do echo %%~fa %%~za >> C:\Temp\VideoList.txt

J'ai remarqué que de très longs chemins de fichiers/noms de fichiers (des centaines de caractères) peuvent également provoquer des erreurs, mais la recherche ne s'arrête pas là. Cependant, le chemin reste incomplet pour votre/vos cible (s). Une fois noté, vous pouvez compenser en commençant plus profondément dans la structure de dossiers pour éliminer cette erreur.

Cette page ss64 présente très bien l’utilisation de la commande dir , listant tous les commutateurs, de nombreuses combinaisons de commutateurs, et montrant plusieurs exemples utiles de syntaxe correcte. Ce n'est pas aussi complet que les différentes communautés de Stack Exchange, mais la présentation est parfaitement claire une fois que vous êtes familiarisé avec les scripts en ligne de commande/batch.

0
user23715