using System.IO;
using System.Security.Cryptography;
private void TraverseDirectory(DirectoryInfo directory, List<Tuple<FileInfo, FileInfo>> doubles, Dictionary<string, FileInfo> hashes)
{
using (var md5 = MD5.Create())
{
foreach (var file in directory.GetFiles())
{
using (var stream = file.OpenRead())
{
var hash = BitConverter.ToString(md5.ComputeHash(stream));
FileInfo alreadyFound;
if (hashes.TryGetValue(hash, out alreadyFound))
{
doubles.Add(Tuple.Create(alreadyFound, file));
}
else
{
hashes.Add(hash, file);
}
}
}
}
foreach (var sub in directory.GetDirectories())
{
TraverseDirectory(sub, doubles, hashes);
}
}
public List<Tuple<FileInfo, FileInfo>> FindDoubles(DirectoryInfo directory)
{
if (directory == null)
{
throw new ArgumentNullException();
}
if (!directory.Exists)
{
throw new FileNotFoundException();
}
var doubles = new List<Tuple<FileInfo, FileInfo>>();
var hashes = new Dictionary<string, FileInfo>();
TraverseDirectory(directory, doubles, hashes);
return doubles;
}