我最近試圖找出比較兩個大型XML文檔和同事推薦對其進行散列並比較散列字符串的最快方法。使用MD5/SHA1比較XML實例
起初,這似乎是一個明顯的/絕妙的主意!但是,然後本能地告訴我,它可能「太好,不真實」。
就像序列化POJO進行比較/克隆被普遍認爲是「不好的做法」一樣,對於這個技術來說也是如此嗎?爲什麼或者爲什麼不?警告/陷阱等?
我最近試圖找出比較兩個大型XML文檔和同事推薦對其進行散列並比較散列字符串的最快方法。使用MD5/SHA1比較XML實例
起初,這似乎是一個明顯的/絕妙的主意!但是,然後本能地告訴我,它可能「太好,不真實」。
就像序列化POJO進行比較/克隆被普遍認爲是「不好的做法」一樣,對於這個技術來說也是如此嗎?爲什麼或者爲什麼不?警告/陷阱等?
讓我先說XML比較是棘手的。這很棘手,因爲您很好地將它放在問題的標題中,您正在比較XML實例。
個XML不只是內容(文本文件,二進制文件等),您可以比較看看是否有不同; XML有意義,不同的XML實例可以具有相同的含義。
例如,考慮這個XML示例:
<sample a="foo" b="bar" />
那是比這有什麼不同?
<sample b='bar' a='foo' />
或本:
<sample
a="foo"
b="bar" />
甚至這個?:
<sample a="foo" b="bar"></sample>
答案是,樣品都是平等的。但是如果你散列每一個,你將會得到不同的哈希值。
如果要散列XML實例並使用散列進行比較,首先必須將它們存入a canonical form。如果XML不經常更改,則可以將散列存儲在XML的旁邊,然後僅對比散列。只有當事物發生變化時才計算消息摘要。這可以非常快。其他
一種解決方案也將是有an XSLT改造和使用這兩個XML實例作爲輸入。然後輸出更簡單的東西(也許是一個包含所有元素和屬性名稱和值的平面文件),這些文件比較簡單。
有lots of ways to compare XML文件和@ violet313在評論中提到,這真的取決於你爲什麼要作一個比較,準確,你要比較的。
我很感謝這個偉大的答案!事後看來,我應該在我的帖子中提到XML實例是由XStream生成的,所以相同的POJO將被轉換爲相同的XML,並且*應該*除非我遺漏了映射到相同哈希值的任何東西。所以我不認爲這對我們來說是一個問題 - 但非常好地指出! – IAmYourFaja 2012-04-16 15:48:57
計算哈希需要讀取整個文件反正花CPU週期計算,所以如果你不擔心的文件在不同但語義相同,爲什麼不能做逐字節的比較?
此外,您引用的散列都有問題(MD5更是如此),如果存在任何風險,有人可能有任何動機創建具有相同散列但不同的文檔(這可以很容易地用MD5這從密碼學的角度來看完全是破碎的,並且可能與SHA1並不遙遠)。
基本上你提出什麼(哈希然後比較哈希值)可能比普通的比較慢(除非你在閱讀一個真正尋求規避媒體),並有自己的問題。這和在XML文檔的背景下,你可能想要一個更高層次的方法,因爲Bogdan非常適合。
冒着鈍的風險,這真的取決於你爲什麼要做一個比較。例如:對於需要記錄更改的備份系統,則採用散列即可。爲了知道兩個文件是相同的還是不同的,字節比較的字節可以非常快(oops!第一個字節不同,這裏停止),而像[Rabin-Karp](http://en.wikipedia。 org/wiki/Rabin-Karp_string_search_algorithm)是O(n) – violet313 2012-04-13 12:07:46