2016-10-14 3 views
0

Nous avons un dossier de données de 150 Go. Dans ce cadre, le contenu du fichier est de n'importe quel format (doc, jpg, png, txt, etc.). Nous devons vérifier tous les contenus de fichiers les uns par rapport aux autres pour vérifier s'il y a du contenu de fichier en double. Si c'est le cas, imprimez la liste des noms de chemin d'accès au fichier. Pour cela, j'ai d'abord utilisé ArrayList<File> pour stocker tous les fichiers, puis utilisé la méthode FileUtils.contentEquals(file1, file2). Quand je l'essaye pour une petite quantité de fichiers (Dossier) ça marche mais pour ce dossier de données 150Gb, ça ne montre aucun résultat. Je pense d'abord stocker tous les fichiers dans un ArrayList fait le problème. JVM problème tas, je ne suis pas sûr.Vérification du contenu du fichier en double à l'aide de Java

Quelqu'un a de meilleurs conseils et un code d'échantillon pour gérer cette quantité de données? Aidez-moi, s'il vous plaît.

+3

Avez-vous essayé de calculer la somme de contrôle du fichier au lieu de les lire? – Prashant

+0

J'ai utilisé directement la méthode FileUtils.contentEquals pour vérifier les fichiers à chercher et stocker le résultat. – Mostafizur

+0

@Prashant pourriez-vous s'il vous plaît écrivez-moi un exemple de code pour cela? – Mostafizur

Répondre

4

Calculez le MD5 hash de chaque fichier et stockez-le dans un HashMap avec le hachage MD5 comme clé et le chemin du fichier comme valeur. Lorsque vous ajoutez un nouveau fichier à HashMap, vous pouvez facilement vérifier s'il existe déjà un fichier avec ce hachage MD5.

La probabilité d'une fausse correspondance est très faible, mais si vous le souhaitez, vous pouvez utiliser FileUtils.contentEquals pour confirmer la correspondance.

par exemple:

void findMatchingFiles(List<String> filepaths) 
{ 
    HashMap<String, String> hashmap = new HashMap<String, String>(); 
    for(String filepath in filepaths) 
    { 
     String md5 = getFileMD5(filepath); // see linked answer 
     if(hashmap.containsKey(md5)) 
     { 
      String original = hashmap.get(md5); 
      String duplicate = filepath; 

      // found a match between original and duplicate 
     } 
     else 
     { 
      hashmap.put(md5, filepath); 
     } 
    } 
} 

Si plusieurs fichiers identiques, cela trouvera un match de chacun d'eux avec le premier, mais pas un match de tous les uns aux autres. Si vous voulez ce dernier, vous pouvez stocker un hachage de la chaîne MD5 à une liste de chemins de fichiers au lieu de seulement au premier.

1

Utilisez une table de hachage et stockez le hachage MD5 du contenu du fichier en tant que valeur de clé et de chemin de fichier. La taille de hachage MD5 est de 16 octets quelle que soit la taille du contenu. Donc, peu importe si vos fichiers sont 150 Go chacun ou même plus gros. Lorsque vous rencontrerez un nouveau fichier, calculez son hachage MD5 et vérifiez s'il est déjà dans le HashTable. La recherche et l'insertion en hashtable seront amorties O(1). En outre, MD5 a très peu de chance de collision. Donc, pour éviter les faux positifs, vous pouvez vérifier le contenu du fichier en cas de correspondance.

Note: Je n'ai pas remarqué en écrivant @samgak a déjà donné une réponse élaborée. Vous pouvez utiliser l'extrait de code sa réponse :)