2009-04-17 10 views
5

Obiekty pochodzące z algorytmu HashAlgorithm, takie jak MD5CryptoServiceProvider, mają metodę Dispose(), ale są prywatne. Zamiast tego używa metody Clear(), która "Uwalnia wszystkie zasoby", z której korzysta..NET: Usuwanie obiektu HashAlgorithm

WTF?

Czy to w ten sposób poprawnie usunąć algorytm HashAlgorithm?

var hasher = new MD5CryptoServiceProvider(); 

byte[] hashCode = hasher.ComputeHash(data); 

hasher.Clear(); 

Ktoś chce mi to wyjaśnić? :)

+0

polecam użyć innego algorytmu mieszającego zbyt jeśli można tak wiele uznają MD5 hash niebezpieczne w niektórych aplikacjach. Dobrą alternatywą może być rodzina SHA, taka jak SHA 256. Są one również dostępne do użytku w .NET. – Skurmedel

+0

Dobre połączenie. Pamiętam, że czytanie MD5 okazało się podatne na ataki kilka lat temu. Geeze, to z Wikipedii: "W dniu 18 marca 2006 roku Klima opublikował algorytm [10], który może znaleźć kolizję w ciągu jednej minuty na pojedynczym notebooku, używając metody, którą nazwał tunelowaniem." – core

Odpowiedz

3

Patrząc z reflektorem, metoda Clear z HashAlgorithm po prostu wywołuje prywatną metodę . Powodem ujawnienia metody o nazwie Clear było prawdopodobnie to, że projektanci klasy uznali, że będzie to bardziej odpowiednia nazwa dla algorytmu mieszania. Podobne style występują w innych częściach BCL, na przykład Close dla System.IO.Stream. Ponadto najlepszą praktyką jest użycie bloku using, który automatycznie wywoła prywatną metodę Dispose po jej zakończeniu.

+0

Jak wspomniano przez innych, najlepiej użyć bloku 'using', co upraszcza logikę try-finally/dispose i jest zalecaną praktyką. – Noldorin

-4

Powinieneś pozwolić GC zająć się tym za Ciebie. To jest praca.

Niektóre zasoby należy usunąć, jak połączenia DB i uchwyty plików, więc umieść je w bloku using (C#). Jednak nie jest to jedna z tych spraw.

+0

W rzeczywistości algorytm HashAlgorithm (a tym samym MD5CryptoServiceProvider) * może * implementować IDisposable, dlatego powinny być odpowiednio usuwane, przez wywołanie metody Clear lub za pomocą bloku 'using'. – Noldorin

+3

Tylko dlatego, że klasa implementuje IDisposable, nie oznacza, że ​​musi być usuwana ręcznie. Do każdego jednak własnego. –

+0

Nie, faktycznie, ale fakt, że * to * implementuje IDisposable prawie zawsze oznacza, że ​​powinien być ręcznie usuwany, ponieważ wykonuje wewnątrz niego natywny interop. W końcu GC może go pozbyć, nawet jeśli nie wywołasz tej metody jawnie, ale czas, w którym to nastąpi, nie ma gwarancji, że wkrótce będzie dostępny. – Noldorin

10

Metoda Dipose() jest prywatna, ale po jej przesłaniu do IDisposable można uzyskać do niej dostęp. Jak powiedzieli inni, Clear() nazwie to za ciebie.

Lepszym rozwiązaniem jest jednak to, aby załączyć deklarację i i przypisanie zmiennej w using() bloku:

byte[] hashCode; 

using(var hasher = new MD5CryptoServiceProvider()) 
{ 
    hashCode = hasher.ComputeHash(data); 
}