36 votes

Quand est-il possible de vérifier si un fichier existe?

Les systèmes de fichiers sont volatiles. Cela signifie que vous ne pouvez pas faire confiance à la suite d'une opération, pour être encore valide pour le prochain, même si c'est la ligne de code suivante. Vous ne pouvez pas dire if (some file exists and I have permissions for it) open the file, et vous ne pouvez pas dire if (some file does not exist) create the file. Il y a toujours la possibilité que le résultat de votre if condition de changement entre les deux parties de votre code. Les opérations sont distinctes: pas atomique.

Pour aggraver les choses, la nature du problème signifie que si vous êtes tenté de faire cette vérification, les chances sont que vous êtes déjà inquiet ou conscients que quelque chose que vous n'avez pas de contrôle est susceptible de se produire dans le fichier. La nature des environnements de développement font de cet événement moins susceptible de se produire au cours de vos tests et très difficile à reproduire. Ainsi, non seulement vous avez un bug, mais le bug n'apparaît pas lors des tests.

Par conséquent, dans des circonstances normales, le meilleur plan d'action est de ne pas même essayer de vérifier si un fichier ou un répertoire existe. Au lieu de cela, mettez votre temps de développement dans la gestion des exceptions dans le système de fichiers. Vous avez à gérer ces exceptions de toute façon, donc c'est une bien meilleure utilisation de vos ressources. Même si des exceptions sont lents, de vérifier l'existence d'un fichier nécessite un voyage supplémentaire sur le disque, et l'accès au disque est beaucoup plus lent. J'ai même un bien voté réponse à cet effet, dans une autre question.

Mais je vais avoir quelques doutes. Dans .Net, par exemple, si c'est vraiment toujours vrai, l' .Exists() méthodes ne serait pas dans l'API en premier lieu. Également envisager des scénarios où vous attendez votre programme à la nécessité de la création d'un fichier. Le premier exemple qui vient à l'esprit est pour une application de bureau. Cette application s'installe par défaut de l'utilisateur du fichier de config à la maison répertoire, et le premier temps de chaque utilisateur démarre l'application, il copie ce fichier pour que l'utilisateur du dossier de données d'application. Elle attend que le fichier n'existe pas sur le premier démarrage.

Alors, quand est-il acceptable de vérifier à l'avance de l'existence (ou d'autres attributs, tels que la taille et les permissions d'un fichier? Attend de l'échec plutôt que de succès à la première tentative d'une bonne règle de pouce?

38voto

Stephen Martin Points 4858

Le Fichier.Existe méthode existe principalement pour tester l'existence d'un fichier lorsque vous n'avez pas l'intention d'ouvrir le fichier. Par exemple test de l'existence d'un fichier de verrouillage dont l'existence vous dit quelque chose, mais dont le contenu ne sont pas significatifs.

Si vous allez ouvrir le fichier, puis vous aurez besoin pour gérer toute exception, quels que soient les résultats d'appels de Fichier.Existe. Donc, en général, il n'y a pas de réelle valeur à l'appeler, dans ces circonstances. Juste utiliser le bon FileMode valeur de l'énumération dans votre méthode ouverte et gérer les exceptions, aussi simple que cela.

EDIT: Même si c'est formulée dans des termes de l' .Net de l'API, il est basé sur le système sous-jacent de l'API. À la fois Windows et Unix ont des appels système (c'est à dire CreateFile) qui utilisent l'équivalent de la FileMode énumération. En fait, dans .Net (ou Mono) le FileMode la valeur est simplement passé à travers l'appel système sous-jacent.

6voto

supercat Points 25534

En règle générale, des méthodes comme File.Exists, ou les propriétés comme l' WeakReference.Alive ou SomeConcurrentQueue.Count ne sont pas utiles comme un moyen de veiller à ce qu'un "bon" état existe, mais peut être utile comme un moyen de déterminer qu'un "mauvais" état existe, sans faire d'inutiles (et probablement contre-productif) de travail. De telles situations peuvent survenir dans de nombreux scénarios impliquant des serrures (et fichiers, car ils comprennent souvent des verrous). Parce que toutes les routines qui ont besoin de se verrouiller sur un ensemble de ressources devraient, dans la mesure du possible, toujours acquérir des verrous sur les ressources dans un ordre cohérent, il peut être nécessaire d'acquérir un verrou sur une ressource qui devrait exister avant l'acquisition d'une ressource qui peut ou ne peut pas exister. Dans un tel scénario, alors qu'il est impossible d'éviter la possibilité que l'on peut verrouiller la première ressource, ne parviennent pas à acquérir la seconde, puis relâchez-la première écluse sans avoir fait aucun travail utile avec elle, de vérifier l'existence de la deuxième ressource avant d'acquérir le verrou sur la première serait de nature à réduire inutile et inutile.

5voto

Mitch Wheat Points 169614

Cela dépend de vos besoins, mais une solution consiste à essayer d’obtenir un descripteur de fichier ouvert exclusif , avec un mécanisme de nouvelle tentative. Une fois que vous avez cette poignée, il sera difficile (ou impossible) pour un autre processus de supprimer (ou de déplacer) ce fichier.

J'ai utilisé du code dans .NET semblable au suivant pour obtenir un descripteur de fichier exclusif, où je m'attends à ce qu'un autre processus soit éventuellement en train d'écrire le fichier:

 FileInfo fi = new FileInfo(fullFilePath);

int attempts = maxAttempts;
do
{
    try
    {
        // Asking to open for reading with exclusive access...
        fs = fi.Open(FileMode.Open, FileAccess.Read, FileShare.None);
    }
    // Ignore any errors... 
    catch {}

    if (fs != null)
    {
        break;
    }
    else
    {
        Thread.Sleep(100);
    }
}
while (--attempts > 0);
 

2voto

derobert Points 26258

Un exemple: vous pourrez peut-être vérifier l'existence de fichiers que vous ne pouvez pas ouvrir (en raison, par exemple, d'autorisations).

Un autre exemple, peut-être meilleur: vous voulez vérifier l'existence d'un fichier de périphérique Unix. Mais ne l'ouvrez certainement pas; son ouverture a des effets secondaires (par exemple, ouvrir / fermer /dev/st0 rembobinera la bande)

1voto

Sunny Milenov Points 10978

Dans l'environnement * nix, une méthode bien établie pour vérifier si une autre copie du programme est déjà en cours d'exécution consiste à créer un fichier de verrouillage. Donc, la vérification de l'existence du fichier est utilisée pour le vérifier.

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