Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Общие вопросы по .NET и C# > Как програмными средствами сравнить файлы


Автор: tarasD 21.11.2007, 18:08
Как програмными средствами сравнить примерно 50 тисяч файлов на идентичность, при этом размер файла может достигать размеров до 2 ГБ. 


Автор: Azzdorf 21.11.2007, 18:58
каким образом сравнить???
по размеру или есть другие параметры????

---------------------

А мо есть конкретное задание - типа найти пару одинаковых???????

Автор: marcusmae 21.11.2007, 19:24
tarasD, если возможно два варианта идентичны и неидентичны, то считайте с файлов хеш суммы (http://www.google.com/search?hl=en&client=opera&rls=ru&hs=aHs&q=CRC+hash&btnG=Search или http://www.google.com/search?hl=en&client=opera&rls=ru&hs=fxC&q=MD5+hash&btnG=Search) и сравнивайте их - если будут равны, то файлы идентичны.

Автор: Domovik 22.11.2007, 09:56
marcusmae, ну для 50 тыс. файлов делать md5 - это жестоко (особенно если учесть возможный размер файлов). Но похоже это единственный приемлемый метод в данной ситуации (ускоряет сравнение в десятки раз). Просто стоит сначала проверять размеры сравниваемых файлов, так как 10кб тхт файл не может быть идентичен 4Гб iso-образу smile

PS никто не знает, есть ли в .Net средства для получения СRC или MD5? Изначально благодарен за ответ.

Автор: stab 22.11.2007, 10:20
MD5 - System.Security.Cryptography.MD5, CRC вроде нет. В любом случае, я бы ручками их сделал, т.к. у меня большие сомнения в производительности стандартной реализации.

Автор: Azzdorf 22.11.2007, 12:16
tarasD было бы проще если бы точнее описал задание - тут бы и исходничек родился, но Domovikпоходу прав, если большой разброс по размеру файлов - я бы разбил файлы на несколько груп по размеру, что-бы оптимизировать в плане скорости

например там файлы до 1000кб
1000кб-10мб
10мб-100мб
выше 100мб

а потом прогнать if-оператором при помощи сравнения with use MD5

думаю так будет быстрееsmile хотя можна и поспорить

Автор: tarasD 22.11.2007, 17:44
Я написал через md5. Программа считает 40 минут 60 тисяч файлов, а надо за 5 минут. Причем я учитивал такой вариант когда два файла за размером не равни, то соответственно  файли не равни.  

Автор: Azzdorf 22.11.2007, 18:06
попробуй вариант с группами - мож реально поможет(притом что МД5 долго)
может есть смысл до 10 или 100 метров сравнивать по МД5 а после по размеру - должно ускорить (попробуй звять для сравнения только файлы до 10 метров и посмотреть сколько выйдет их сравнение через МД5)

также вопросик какого размера в основном файлы???? и где содержаться файлы и как часто необходимо проводить такое сравнение??? smile 

Автор: marcusmae 22.11.2007, 21:14
Цитата(tarasD @  22.11.2007,  17:44 Найти цитируемый пост)
Программа считает 40 минут 60 тисяч файлов, а надо за 5 минут.


Узкие места :

1) КОД
Если под .NET пишите, то неудивительно, что медленно. Возьмите какую-нибудь из программок, проверяющих контрольные суммы (коих http://www.google.com/search?hl=en&client=opera&rls=ru&hs=mZG&q=Check+MD5+&btnG=Search, например, http://www.brandonstaggs.com/filecheckmd5/) и сравните их скорость со своей программой на каком-нибудь одном файле. Прирост скорости могла бы дать реализация под native С. Если всё грамотно сделать, то ускорение в 8 раз в принципе достижимо smile

2) ДИСК
Магнитные диски работают медленно и, чтобы добиться большего, нужно упорядочивать файлы. Ко множеству мелких файлов долго обращаться по файловой системе. Можно объединить в более крупные архивы (или "непрерывные" файлы другого вида) - возможно, будет жеваться быстрее. Этим или другим образом желательно добиться того, чтобы данные, которые Вы анализируете были бы как можно меньше фрагментированы по диску.

Автор: Azzdorf 23.11.2007, 11:14
может сделать как на многих крупных серверах - создать файл-регистр, к котором хранить даные о файле (расположение, размер...) и в т.ч. МД5 - у по надобности пробигать и сравнивать???

или общая задача другая????

Автор: ivashkanet 23.11.2007, 11:26
Цитата(Azzdorf @  23.11.2007,  11:14 Найти цитируемый пост)
может сделать как на многих крупных серверах - создать файл-регистр, к котором хранить даные о файле (расположение, размер...) и в т.ч. МД5 - у по надобности пробигать и сравнивать???

Да, этот вариант мне тоже по душе.

1) За первый прогон создать "индексный" файл с инфой "файл & размер". 
2) Потом пройтись по файлу и найти группы файлов с одинаковым размером (групп будет не много, потому что почти нереально, чтобы разные файлы содержали одинаковое количество байт).
3) Каждую группу проверить MD5.

Автор: marcusmae 23.11.2007, 11:59
Цитата(ivashkanet @  23.11.2007,  11:26 Найти цитируемый пост)
Да, этот вариант мне тоже по душе. За первый прогон создать "индексный" файл с инфой "файл & размер". 


Хм, не годится : файлы можно будет подменить. По размеру Вы не определите, произошло ли это.

Автор: ivashkanet 23.11.2007, 12:07
Цитата(marcusmae @  23.11.2007,  11:59 Найти цитируемый пост)
файлы можно будет подменить

Это может произойти в любой момент сравнения. Какой бы алгоритм ты ни избрал  smile 

P.S. marcusmae, по контексту понятно, что ты подразумеваешь что-то особенное под "подменить". Только вот я не пробью что smile 
Давай на ты

Добавлено через 42 секунды
Цитата(ivashkanet @  23.11.2007,  11:26 Найти цитируемый пост)
1) За первый прогон создать "индексный" файл с инфой "файл & размер". 

Кста, "файл" спокойно поместится в оперативке

Автор: 1stain 23.11.2007, 12:08
как вариант, если есть сервер с базой данных, занести туда записи для всех контролируемых файлов. При первом прогоне - проверить все фалы на идентичность, поставить отметку в полях "synchronized" & "equal". Далее, на кадой машине, где лежат проверяемые файлы крутицца сервис виндовз, который в рантайме отслеживает изменение файлов с помощью FileSystemWatcher и сбрасывает в базе у записи, соответстующей измененному файлу признак "synchronized". При проведении очередной проверки, проверяем только те записи, у которых сброшен "synchronized" и после проверки опять же его поднимаем...

з.ы. правда, при каждом запуске сервиса, он должен определить, были ли изменены проверяемые файлы за время его (сервиса) простоя

Автор: marcusmae 23.11.2007, 12:38
Цитата(ivashkanet @  23.11.2007,  12:07 Найти цитируемый пост)
marcusmae, по контексту понятно, что ты подразумеваешь что-то особенное под "подменить".


Ну можно, действительно, нехитрым сишным кодом подвинуть дату модификации файлов лет эдак на десять в прошлое или в будущее smile Только зачем? Просто, скажем, какой-нибудь фоновый процесс взял и обновил один из файлов - вот и всё, кэшированные суммы уже не действительны...

Цитата(ivashkanet @  23.11.2007,  12:07 Найти цитируемый пост)
Это может произойти в любой момент сравнения. Какой бы алгоритм ты ни избрал 


Так, и что? = Алгоритм подмену заметит, а твой индексер просто выдаст значение из базы и будет неправ.  Или, как предлагает 1stain, кеширование должно работать в связке с системными сервисами по доступу к файловой системе. Типа, уже почти Windows Vista smile 

Автор: ivashkanet 23.11.2007, 13:29
Цитата(tarasD @  21.11.2007,  18:08 Найти цитируемый пост)
примерно 50 тысяч файлов 
 первый прогон пройдет за 10 сек, потом в течении 10 сек он создаст группы и, так как групп немного, он сравнит хэши еще за 10 сек.

И не нужно усложнять задачу, придумывая разные возможные и невозможные условия использования.

P.S. 
Цитата(marcusmae @  23.11.2007,  12:38 Найти цитируемый пост)
Алгоритм подмену заметит, а твой индексер просто выдаст значение из базы и будет неправ

C какой кстати?

Автор: VisualProgrammerNET 23.11.2007, 16:42
Согласен с ivashkanet.

Хотя я не совсем конкретно понимаю задачу... Сравнивать нужно файлы на одном отдельном компе или создавать нечто подобное p2p-сетям, где сравниваются файлы с разных компьютеров?

В первом случае всё просто. Как описали выше, сравниваются размеры файлов, при их совпадении сравниваются хеш-суммы. В случае многих компьютеров без центральной БД не обойтись. Решить можно так:

При первом запуске программы, она анализирует все разрешённые для сканирования файлы и отправляет на центральный сервер инфу о файле (id компа, название файла, его размер). Когда происходит поиск по названию, смотрятся файлы, удовлетворяющие условию. Файлы с одинаковым размером хешируются, тем самым проверяется их совпадение. Это сводит к минимуму хеширование и поиск получается достаточно быстрым.

Чё-то с похмелья мысли путаются =)) Но в принципе чё-то типа этого =)

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)