2010-02-22 258 views
7

我有一個程序比較兩個文件夾中的文件。我想檢測文件是否已被重命名,確定最新的文件(最近重命名),並更新舊文件中的名稱以匹配。如何確定文件最近被重命名的時間?

要做到這一點,我會檢查最新的文件是否與舊的文件一點一點地相同,如果是,只需重命名舊文件以匹配新文件。

問題是,我沒有任何關鍵要告訴我哪個文件最近被重命名。

我會喜歡FileInfo.LastModified的一些屬性,但對於已被重命名的文件。

我已經看過像FileSystemWatcher這樣的解決方案,這並不是我正在尋找的。我希望能夠隨時運行我的同步器,而不必擔心跟蹤文件夾狀態的某個專用進程。

任何想法?

回答

1

答:至少在NTFS,您可以將alternate data streams to a file。 在第一次同步時,您可以將ADS中的GUID附加到源文件以標記它們。

B:如果您沒有對源代碼的寫入權限,請在您的目標存儲庫中存儲同步文件的散列值。當源更改時,只需散列源文件,並且只在散列衝突時逐位進行比較。根據散列函數的質量和速度,這將爲您節省大量時間。

+0

...當然,將它與'LastModified'結合起來。 – 2010-02-22 23:37:42

+0

我已經在每一端存儲了目錄的哈希值。逐位匹配數據已經成爲可能。我只是希望當移動預先存在的文件在慢速網絡上同步時,我可以節省一些帶寬。它看起來像沒有非NTFS特定的方式來做到這一點。 – 2010-02-23 17:17:59

+0

這也可以在映射的驅動程序(或網絡共享)上工作,前提是源卷是NTFS。 如果你還沒有找到它,這可能有一些幫助: http://www.codeproject.com/KB/cs/ntfsstreams.aspx – 2010-02-23 22:45:11

0

您可能會創建一個配置文件,其中包含文件夾中所有預期名稱的列表,然後,如果該文件夾中的文件不是預期的名稱列表的成員,則確定該文件已經重命名。但是,這會增加另一層工作,因爲每次要將新文件添加到文件夾時都必須更改列表。

+0

這並不適用於我的工具。它意味着在兩個方向上同步任何兩個目錄。 – 2010-02-22 22:51:40

+0

你有沒有試過比較?這是您尋找的最佳工具。 – Aaron 2010-02-22 22:52:34

0

文件系統通常不會跟蹤它。

由於您似乎在Windows上,您可以使用GetFileInformationByHandle()。 (對不起,我不知道C#等價物)。您可以使用返回的結構體中的「文件索引」字段來查看文件是否具有與您以前見過的相同的索引。請記住,硬鏈接也將具有相同的索引。

或者你可以以某種方式散列文件內容。

我不知道你想要做什麼,所以我不能告訴你這兩點之一是否合理。這可能是最合理的答案,「不,你做不到。」

+0

我很確定這不是OP正在尋找的東西,但它仍然是一個有趣的想法......可能比OP的測試計劃更好,如果這兩個文件是位相同的以確定重命名已執行。 – rmeador 2010-02-22 23:28:28

+0

這是個好主意,但是文件ID有很多問題。備註部分說:「存儲在nFileIndexHigh和nFileIndexLow成員中的標識符被稱爲文件ID。[如此高索引和低索引=> **文件ID **]支持**文件ID ** s是文件特定於系統的[所以,不是所有的文件系統都可以支持它... NTFS可能會這樣做,誰知道其他的文件系統是否會這樣做]。文件ID不能保證隨着時間的推移是唯一的,因爲文件系統可以自由地重複使用[我想]時間快照,在某些情況下,文件的文件ID可能會隨着時間而改變。「 – Alexandru 2014-11-07 20:29:45

1

如果您在NTFS驅動器上運行,則可以啓用change journal,然後您可以查詢重命名事件等內容。但是,您需要成爲一名管理員才能使用它,並且會使用磁盤空間。不幸的是,我不知道閱讀期刊的任何具體的C#實現。

0

我會用存儲上次更新時間的2個目錄中的(所有?)文件的CRC值(例如,CRC example)與CRC值,文件名等進行比較。之後,通過CRC查找mach列表然後使用日期值來決定要做什麼。

+0

我已經這樣做了。問題是重命名文件不會修改任何時間戳。 – 2010-02-23 17:14:16

+0

哦 - 據我所知,你不能重命名文件,也不能修改它的時間戳。如果可以的話,它會是一個相當低級別的API調用(不可能由C#公開) – 2010-02-23 21:06:55