![](/img/trans.png)
[英]Efficient way to share the same interface implementation between two or more classes
[英]More efficient way to compare two huge directories and replace same files
F:/original_images
, E:/resized_images
我有兩個硬盤,其中包含很多目錄和image(jpg)文件,每個硬盤的總大小約為1.5TB(原始)和400GB(調整大小) 。
每個都有相同的文件名,但大小不同(調整大小)。 然后,我必須用原件替換調整后的尺寸。 不幸的是, 每個目錄層次結構完全不同。
我設法完成了這項工作,但是確實需要很長時間。 我希望幾天能完成。 它有兩個循環( Files.walkFileTree()
),它們僅搜索從A到Z的匹配項。一點都不聰明。
public static void main(String[] args) throws IOException {
FileWriter ostream = new FileWriter("result.txt");
BufferedWriter out = new BufferedWriter(ostream);
String fromDir = "F:/original_images";
String toDir = "E:/resized_images";
final Path source = Paths.get(fromDir);
final Path target = Paths.get(toDir);
Files.walkFileTree(source, EnumSet.of(FileVisitOption.FOLLOW_LINKS), Integer.MAX_VALUE,
new SimpleFileVisitor<Path>() {
@Override
public FileVisitResult visitFile(Path sourceFile,
BasicFileAttributes attrs) throws IOException {
// if jpg (there are no jpeg)
if(sourceFile.toString().toLowerCase().endsWith("jpg")) {
// search for the matching file
// start ** inner of [Files.walkFileTree()]
Files.walkFileTree(target, EnumSet.of(FileVisitOption.FOLLOW_LINKS), Integer.MAX_VALUE,
new SimpleFileVisitor<Path>() {
@Override
public FileVisitResult visitFile(Path Targetfile, BasicFileAttributes attrs) throws IOException {
if(sourceFile.getFileName().equals(Targetfile.getFileName())) {
out.write("replace : [" + sourceFile + "] -> [" + Targetfile + "]");
try {
// copy..
Files.copy(sourceFile, Targetfile, REPLACE_EXISTING);
}catch(Exception e) {
out.write(e.toString());
}
// stop searching for this file.
return FileVisitResult.TERMINATE;
}else
return FileVisitResult.CONTINUE;
}
});
// end ** inner of [Files.walkFileTree()]
}
return FileVisitResult.CONTINUE;
}
});
out.write("[completed folder] " + fromDir);
out.close();
}
我相信一定有更聰明的方法。
(我的猜測是將文件名存儲在索引數組中,因為比較起來要快得多。)
你會怎么做?
更新 (已解決)
通過采用兩個答案的想法,我終於做到了。
源代碼太長,無法顯示,但簡潔的是:
循環'resized_images'並將files_info存儲到hashmap(key:file_name,value:full_Path)中。
循環'original_images'並將files_info存儲到hashmap(key:file_name,value:full_Path)中。 為了提高效率,我為每個子目錄制作了每個哈希圖。
比較並替換每個“調整大小”和“原始”哈希圖。
結果比以前快得多。 大多數執行時間是在復制文件時。 除此之外,它不到10分鍾。
我的觀察方式有兩個子問題:
在上面列出的方法中,您在源目錄中遞歸地進行迭代,我們稱其為外循環。 然后,對於源目錄中的每個文件,您都在目標目錄中進行遞歸迭代,讓我們將其稱為內部循環。 多數民眾贊成在O(n2)(讀為n平方的大哦)方法。
另一種簡單的方法可能是,創建兩個映射(哈希映射),鍵為文件名。 因此,您將必須遞歸地分別遍歷兩個目錄,即分別遍歷循環。
然后遍歷較小的哈希圖,然后替換調整大小的圖像。
那將是一種O(n)方法。 隨着n的不斷增長,您應該看到所花費的時間有了顯着的改善。
如Sanket Naik所述,為原始圖像創建一個Map。 我不確定您的實現效果如何,但是您可以在mkyong中輕松編輯此代碼。
在Map
存儲中,將image_name.jpg
作為key
並將其its_directory
作為值。 例如, img1.jpg
位於F:/original_images/dir1/dir2/dir3/
,相應的條目應為img1.jpg, /dir1/dir2/dir3/
。
然后,
for each entry in resized image directory{
value = map.get(entry);
replaceImage(path/to/entry/+entry, value+entry);
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.