2009-11-02 6 views
2

Une question très similaire a également été posée here on SO au cas où vous êtes intéressé, mais comme nous le verrons la réponse acceptée de cette question n'est pas toujours le cas (et ce n'est jamais le cas pour mon application-pattern d'application).FileStream très lent sur demande-démarrage à froid

Le code de détermination des performances se compose du constructeur FileStream (pour ouvrir un fichier) et d'un hachage SHA1 (l'implémentation du framework .Net). Le code est à peu près la version C# de ce qui a été demandé dans la question que j'ai liée à ci-dessus.

Cas 1: L'application est démarrée pour la première fois ou pour la nième fois, mais avec un jeu de fichiers cible différent. L'application est maintenant dit de calculer les valeurs de hachage sur les fichiers qui n'ont jamais été consultés auparavant.

  • ~ 50ms
  • 80% constructeur FileStream
  • 18% calcul de hachage

Cas n ° 2: L'application est maintenant complètement terminée, et a commencé à nouveau, demandé de calculer hachage sur le même fichiers:

  • ~ 8ms
  • 90% de calcul de hachage
  • 8% constructeur FileStream

Problème
Mon application est toujours en cours d'utilisation Cas 1. Il ne sera jamais demandé de recalculer un hachage sur un fichier déjà visité une fois.

Donc, mon étape de détermination du débit est FileStream Constructor! Y at-il quelque chose que je puisse faire pour accélérer ce cas d'utilisation?

Merci.

P.S. Les statistiques ont été recueillies à l'aide du profileur JetBrains.

+0

Je vois exactement le même comportement. L'utilisation de ReadAllBytes et le calcul du hachage prennent peu de temps mais peuvent être terribles sur la mémoire (en fonction de la taille du fichier). J'ai donc essayé de passer un FileStream au computehash de MD5 ($ stream) et de voir des résultats complètement inacceptables. Les temps de résultat sont des ordres de grandeur en différence ... – thepip3r

Répondre

1

Le système de fichiers et/ou le contrôleur de disque mettent en cache les fichiers/secteurs récemment accédés. L'étape qui détermine le débit est la lecture du fichier, pas la construction d'un objet FieStream, et il est tout à fait normal qu'il soit beaucoup plus rapide lors de la seconde exécution lorsque les données sont dans le cache.

+0

Je ne crois pas que ce soit le cas. Le constructeur FileStream ne lit pas le fichier entier, la fonction de hachage appelle dans ce but. Mais c'est le constructeur qui prend 80% du temps. –

0

Vous devriez essayer d'utiliser le FILE_FLAG_SEQUENTIAL_SCAN natif, vous devrez Pinvoke CreateFile afin d'obtenir une poignée et le transmettre à FileStream

+0

N'utilise pas le [constructeur] (http://msdn.microsoft.com/en-us/library/ms143396.aspx) qui accepte un ['FileOptions'] (http://msdn.microsoft.com/ en-us/library/system.io.fileoptions.aspx) faites-le déjà dans le flux si vous le passez 'FileOptions.SequentialScan'? EDIT: oui, il regarde dans la source de référence que le paramètre enum est retourné dans le 'dwFlagsAndAttributes' de' CreateFile', et la valeur de l'enum est '0x08000000' qui est la même valeur que' FILE_FLAG_SEQUENTIAL_SCAN' –