Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "KOL";
Текущий архив: 2009.07.26;
Скачать: [xml.tar.bz2];

Вниз

Как быстро сравнить два файла?   Найти похожие ветки 

 
andreil ©   (2008-02-26 20:26) [0]

Для VCL это выглядело следующим образом:
function CompareFiles(const File1, File2:TFileName): boolean;
var
 ms1, ms2: pStream;
begin
 Result:=False;
 ms1:=TMemoryStream.Create;
 try
   ms1.LoadFromFile(File1);
   ms2:=TMemoryStream.Create;
   try
     ms2.LoadFromFile(File2);
     if ms1.Size=ms2.Size then Result:=CompareMem(ms1.Memory, ms2.Memory, ms1.Size);
   finally
     ms2.Free;
   end;
 finally
   ms1.Free;
 end
end;


Мне хотелось бы узнать, как такое можно сделать на КОЛ, если вообще возможно. И желательно - потоками, тк они быстрее работают.


 
Jon ©   (2008-02-27 00:18) [1]

function CompareFiles(const File1, File2: String): Boolean;
var
 fs1, fs2, ms1, ms2: PStream;
begin
 Result := False;
 fs1 := NewReadFileStream(File1);
 fs2 := NewReadFileStream(File2);
 ms1 := NewMemoryStream;
 ms2 := NewMemoryStream;
 Stream2Stream(ms1, fs1, fs1.Size);
 Stream2Stream(ms2, fs2, fs2.Size);
 if ms1.Size = ms2.Size then
   Result := CompareMem(ms1.Memory, ms2.Memory, ms1.Size);
 ms2.Free;
 ms1.Free;
 fs2.Free;
 fs1.Free
end;


 
andreil ©   (2008-02-27 08:51) [2]


> function CompareFiles(const File1, File2: String): Boolean;
> var  fs1, fs2, ms1, ms2: PStream;begin  Result := False;
>   fs1 := NewReadFileStream(File1);  fs2 := NewReadFileStream(File2);
>   ms1 := NewMemoryStream;  ms2 := NewMemoryStream;  Stream2Stream(ms1,
>  fs1, fs1.Size);  Stream2Stream(ms2, fs2, fs2.Size);  if
> ms1.Size = ms2.Size then    Result := CompareMem(ms1.Memory,
>  ms2.Memory, ms1.Size);  ms2.Free;  ms1.Free;  fs2.Free;
>   fs1.Freeend;


Вылетает с ошибкой после первого же обращеня :(. Те до конца доходит и все - ошибка :(


 
Palladin ©   (2008-02-27 12:16) [3]

потоки быстрее работают... от ведь... а мужики то и не знают...

Function CompareFiles(Const p_strFileName1,p_strFileName2:String):Boolean;
Const
BUF_SIZE=1024*1024;
Var
 f1,f2:File;
 buf1,buf2:Pointer;
 n1,n2:Integer;
Begin
 AssignFile(f1,p_strFileName1);Reset(f1,1);
 AssignFile(f2,p_strFileName2);Reset(f2,1);
 Result:=FileSize(f1)=FileSize(f2);
 If Result Then
  Begin
   GetMem(Buf1,BUF_SIZE); GetMem(Buf2,BUF_SIZE);
   Try
    Repeat
     BlockRead(f1,Buf1^,BUF_SIZE,n);
     BlockRead(f2,Buf2^,BUF_SIZE,n);
     Result:=CompareMem(Buf1,Buf2,n);
     If Not Result Then Break;
    Until n=0;
   Finally
    FreeMem(Buf1); FreeMem(Buf2);
   End;
 CloseFile(f1);CloseFile(f2);
End;


 
andreil ©   (2008-02-27 15:54) [4]

Неа, сильно медленный :( Тот кусок, что я привел повыше перевирал 3Гб за 15 минут, а этот код - за час, не меньше :(


 
Dimaxx ©   (2008-02-27 16:39) [5]

Ну а как ты хотел 2 файла по 3 гига в память пихать (даже 2 по 1,5 и то долго)... :)


 
Palladin ©   (2008-02-27 17:32) [6]


> andreil ©   (27.02.08 15:54) [4]

ффигеть, как же"шь он у тебя 6 гигабайт то в память считал? ты волшебник? а ms1.size ты проверял? сколько же считалось то? а то приходил тут один волшебник... с волшебным файлом подкачки... и компилятором делфи под Win512... тоже гигабайтами в память читал...


 
Тыщ   (2008-02-27 18:17) [7]

Быстрей всего файлы читать с помощью File Mapping, кусками по 4 или 8 мб.


 
andreil ©   (2008-02-28 09:08) [8]

Я имею ввиду ФАЙЛЫ, а не ФАЙЛ. Мне надо в программе сравнивать файлы игр для создания патчей. Для VCL"а у меня был набор функций для этого, а для KOL"а надо писать все самому ;) Просто я сделал так:
function CompareFiles(const File1, File2:TFileName): boolean;
var
 ms1, ms2: pStream;
begin
 Result:=False;
 try
   ms1:=NewReadFileStream(File1);
   try
     ms2:=NewReadFileStream(File2);
     if ms1.Size=ms2.Size then Result:=CompareMem(@ms1.Memory, @ms2.Memory, ms1.Size);
   finally
     ms2.Free;
   end;
 finally
   ms1.Free;
 end
end;


но этот код практически всегда выдает несоответствие файов :(


 
Palladin ©   (2008-02-28 11:37) [9]


> Я имею ввиду ФАЙЛЫ, а не ФАЙЛ.

А где тебе говорили про ФАЙЛ, а не ФАЙЛЫ? чудик
да не можешь ты прочитать себе в память больше чем 2гб минус <скушанное твоей программой уже>, нет таких компиляторов для делфи

Function CompareFiles2(Const p_strFileName1,p_strFileName2:String):Boolean;
Const
BUF_SIZE=32*1024*1024;

Type
TFileMapRec=Record
 _File:HFILE;
 _Map:THandle;
 _Size:Int64;
End;

Function OpenFile(Const p_strFileName:String):TFileMapRec;
Var
 slo,shi:Cardinal;
Begin
 Result._File:=CreateFile(PChar(p_strFileName),GENERIC_READ,FILE_SHARE_READ,Nil,O PEN_EXISTING,FILE_ATTRIBUTE_NORMAL,0);
 slo:=Windows.GetFileSize(Result._File,@shi);
 Int64Rec(Result._Size).Lo:=slo;
 Int64Rec(Result._Size).Hi:=shi;
 Result._Map:=CreateFileMapping(Result._File,Nil,PAGE_READONLY,0,0,Nil);
End;

Procedure CloseFile(Var rp_rFile:TFileMapRec);
Begin
 CloseHandle(rp_rFile._Map);
 CloseHandle(rp_rFile._File);
End;

Function MapBuff(p_rFile:TFileMapRec;p_nFrom:Int64;p_nCount:Cardinal):Pointer;
Begin
 Result:=MapViewOfFile(p_rFile._Map,FILE_MAP_READ,Int64Rec(p_nFrom).Hi,Int64Rec(p _nFrom).Lo,p_nCount);
End;

Procedure UnMapBuff(Var p:Pointer);
Begin
 UnmapViewOfFile(p);
End;

Var
File1,File2:TFileMapRec;
Buf1,Buf2:Pointer;
p:Int64;

Function Compare(p_nFrom:Int64;p_nCount:Cardinal):Boolean;
Begin
 Buf1:=MapBuff(File1,p_nFrom,p_nCount);
 Try
  Buf2:=MapBuff(File2,p_nFrom,p_nCount);
  Try
   Result:=CompareMem(Buf1,Buf2,p_nCount);
  Finally
   UnMapBuff(Buf2);
  End;
 Finally
  UnMapBuff(Buf1);
 End;
End;

Begin
File1:=OpenFile(p_strFileName1);
Try
 File2:=OpenFile(p_strFileName2);
 Try
  Result:=File1._Size<>File2._Size;
  If Result Then Exit;
  p:=0;
  While True Do
   Begin
    If (p+BUF_SIZE)>File1._Size Then
     Begin
      Result:=Compare(p,File1._Size-p);
      Break;
     End Else
     Begin
      Result:=Compare(p,BUF_SIZE);
      If Not Result Then Break;
      Inc(p,BUF_SIZE);
     End;
   End;
 Finally
  CloseFile(File2);
 End;
Finally
 CloseFile(File1);
End;
End;


так должно побыстрее сравнить, пробуй


 
Dimaxx ©   (2008-02-28 13:12) [10]


> NewReadFileStream(File1);


и


> CompareMem(@ms1.Memory, @ms2.Memory, ms1.Size)

Ничего необычного не замечаешь?


 
Palladin ©   (2008-02-28 13:28) [11]

кстати да... бред еще тот...


 
D[u]fa   (2008-02-28 16:05) [12]

>да не можешь ты прочитать себе в память больше чем 2гб минус <скушанное твоей программой уже>, нет таких компиляторов для делфи

я чет про компиляторы не понял)


 
Palladin ©   (2008-02-28 16:23) [13]


> D[u]fa   (28.02.08 16:05) [12]

нет компиляторов делфи способных генерировать, исполняемые в 64разрядной среде, файлы

.NET - не рассматриваем


 
Palladin ©   (2008-02-28 16:24) [14]

*в нативной 64 разрядной среде, без всяких эмуляций 32 разрядов


 
D[u]fa   (2008-02-28 20:18) [15]

а ТСу надо в 64 разрядной среде файлы сравнивать?
видимо я не заметил


 
Palladin ©   (2008-02-29 11:23) [16]

какому ТСу? ты о чем вообще? и чего ты не заметил? я лишь сказал что приложение может использование более 2Гб (более 3Гб при использовании AWE) только при наличии 64разрядной адресации памяти. хотя автор заявляет что у него за 15 минут считались и сравнились 2(два) 3х (трех) гигабайтных (гигабайтных) файла (итого 6 гигабайт) в адресном пространстве его приложения. как ты думаешь с чего вдруг я завел разговор о волшебниках? чего тебе еще непонятно?


 
andreil ©   (2008-02-29 11:49) [17]


> А где тебе говорили про ФАЙЛ, а не ФАЙЛЫ? чудикда не можешь
> ты прочитать себе в память больше чем 2гб минус <скушанное
> твоей программой уже>, нет таких компиляторов для делфи

Да тутже:

> ффигеть, как же"шь он у тебя 6 гигабайт то в память считал?
>  ты волшебник? а ms1.size ты проверял? сколько же считалось
> то? а то приходил тут один волшебник... с волшебным файлом
> подкачки... и компилятором делфи под Win512... тоже гигабайтами
> в память читал...

:)

А за код - спасибо, посмотрим на скорость...


 
Palladin ©   (2008-02-29 12:03) [18]


> ффигеть, как же"шь он у тебя 6 гигабайт то в память считал?

он это имеется ввиду код, 6Гб это имеется в виду 2 файла по 3 гигабайта, почему это невозможно см пост выше.



Страницы: 1 вся ветка

Форум: "KOL";
Текущий архив: 2009.07.26;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.5 MB
Время: 0.009 c
15-1243283277
dis12345
2009-05-26 00:27
2009.07.26
Установка delphi


15-1243020716
AlexDan
2009-05-22 23:31
2009.07.26
Отображение огня.


2-1243760103
dumb
2009-05-31 12:55
2009.07.26
Последовательно выполнить процедуры


15-1242851404
Юрий
2009-05-21 00:30
2009.07.26
С днем рождения ! 21 мая 2009 четверг


8-1195919381
S7r
2007-11-24 18:49
2009.07.26
Загрузка png из потока в gdiplus.





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский