Top.Mail.Ru
Мастера DELPHI, Delphi programming community Титульная страница Поиск, карта сайта Написать письмо 
| Новости | Поиск | FAQ | Статьи | Книги | Новости VCL |
| Форумы ЧАТ | Орешник | KOL и MCK |
Форумы -» Основная («Начинающим»)/ Базы / WinAPI / Компоненты / Сети / Media / Игры / Corba и COM / KOL / FreePascal / .Net / Прочее / RSDN.ORG

« предыдущая ветвь | форум | следующая ветвь »

Быстрое чтение файла [D5, Win95/98]


Страницы:   1 2 3 4 5

Кастуся ©   (2004-06-21 22:46:00) 

мастера, хелп!
обрабатываю файл "дедовским" методом: построчно читаю данные и со строкой делаю все необходимое.
Но не устраивает скорость. На P-I-133 файл в обрабатывает за . Можно ли увеличить скорость на стадии чтения? (Обработка прочитанной строки оптимизированна до максимума) Я знаю, использовать либо BlockRead либо TFileStream но там надо читать буферами, для этого надо знать где строка заканчивается. А можно как-нибудь построчно читать?
Хотел попробовать сл. код:

Start := Stream.Position;
End := Start;
Repeat

Stream.Read(Buffer^, 1024);
CRPos := FindCR(Buffer^);   { где FindCR возвращает 0..1023 для CR,
и 1024, если он не найден}
Inc(End, CRPos);
Until CRPos < 1024;
GetMem(MyPChar, End - Start);  { Здесь может быть +-1 -- мне лень сегодня проверять! }
Stream.Seek(Start);
Stream.Read(MyPChar^, End - Start)

но что такое FindCR?
В общем как тут быть. Дело срочное, хелп плиз!!!


Fay   (2004-06-24 14:22:00) [21]

Моя версия на основе www.shegeda.by.ru [60]
8)
unit MappedFile;

interface

uses
 Windows, SysUtils;

type
 TMappedFile = class
 private
   FHandle : DWORD;
   FMapping : DWORD;
   FSize : DWORD;
   FView : PChar;
   FActive : Boolean;
   FName : string;
   procedure SetSize(const Value : DWORD);
   procedure SetName(const Value : string);
   procedure SetActive(const Value : Boolean);
   function GetActive : Boolean;
 public
   constructor Create;
   destructor Destroy; override;
   procedure Close;
   procedure Open;
   property Size : DWORD read FSize write SetSize;
   property Data : PChar read FView;
   property Active : Boolean read GetActive write SetActive;
   property Name : string read FName write SetName;
 end;

implementation

constructor TMappedFile.Create;
begin
 FHandle := INVALID_HANDLE_VALUE;
 FName := '';
end;

destructor TMappedFile.Destroy;
begin
 Close;
 inherited;
end;

procedure TMappedFile.SetName(const Value : string);
begin
 if Active then
   raise Exception.Create('Нельзя изменить имя!');
 FName := Value;
end;

procedure TMappedFile.SetSize(const Value : DWORD);
begin
 if Active then
   raise Exception.Create('Нельзя изменить размер!');
 FSize := Value;
end;

procedure TMappedFile.SetActive(const Value : Boolean);
var
 sz : DWORD;
begin
 if FActive = Value then Exit;
 if Value then
   begin
     FHandle := CreateFile(
       PChar(FName),
       GENERIC_READ or GENERIC_WRITE,
       FILE_SHARE_READ,
       nil,
       OPEN_EXISTING,
       FILE_FLAG_RANDOM_ACCESS,
       0);
     if FHandle = INVALID_HANDLE_VALUE then
       RaiseLastOSError;
     sz := GetFileSize(FHandle, nil);
     if FSize > sz then
       begin
         SetFilePointer(FHandle, FSize, nil, FILE_BEGIN);
         SetEndOfFile(FHandle);
         SetFilePointer(FHandle, 0, nil, FILE_BEGIN);
       end
     else
       FSize := sz;
     FMapping := CreateFileMapping(
       FHandle,
       nil,
       PAGE_READWRITE,
       0, FSize,
       nil);
     if FMapping = 0 then
       begin
         CloseHandle(FHandle);
         FHandle := INVALID_HANDLE_VALUE;
         RaiseLastOSError;
       end;
     FView := MapViewOfFile(
       FMapping,
       FILE_MAP_ALL_ACCESS,
       0, 0,
       0);
     if FView = nil then
       begin
         CloseHandle(FHandle);
         CloseHandle(FMapping);
         FHandle := INVALID_HANDLE_VALUE;
         FMapping := 0;
         RaiseLastOSError;
       end;
     FSize := GetFileSize(FHandle, nil);
   end
 else
   begin
     UnmapViewOfFile(FView);
     CloseHandle(FMapping);
     CloseHandle(FHandle);
     FView := nil;
     FMapping := 0;
     FHandle := INVALID_HANDLE_VALUE;
   end;
 FActive := Value;
end;

function TMappedFile.GetActive : Boolean;
begin
 Result := FHandle <> INVALID_HANDLE_VALUE;
end;

procedure TMappedFile.Open;
begin
 Active := True;
end;

procedure TMappedFile.Close;
begin
 Active := False;
end;

end.


Fay   (2004-06-24 13:06:00) [22]

function TMappedFile.GetIsOpen: boolean;
begin
Result := FHandle <> DWORD(-1);
end;


  (2004-06-24 12:59:00) [23]

Удалено модератором


Fay   (2004-06-24 12:55:00) [24]

Можно глупый вопрос? А зачем вот такие FHandle:=0;штуки?!


  (2004-06-24 12:46:00) [25]

Удалено модератором


Fay   (2004-06-24 12:37:00) [26]

2www.shegeda.by.ru   (24.06.04 12:27) [58]
Код скорее "для PChar". Delphi в таком случае лепит вполне пригодный код, хотя на asm-е легко сделать лучше 8).


  (2004-06-24 12:27:00) [27]

Удалено модератором


Anatoly Podgoretsky   (2004-06-24 12:22:00) [28]

www.shegeda.by.ru   (24.06.04 11:46) [54]
Так и продолжаешь провоцировать на неприятности в системе?


Fay   (2004-06-24 12:19:00) [29]

2www.shegeda.by.ru   (24.06.04 11:46) [54]
Как Вы думаете, для чего Delphi вызывает UniqueStringA?


  (2004-06-24 12:07:00) [30]

Удалено модератором


  (2004-06-24 11:46:00) [31]

Удалено модератором


Anatoly Podgoretsky   (2004-06-24 11:32:00) [32]

www.shegeda.by.ru   (24.06.04 09:48) [45]
Ты диверсант?


Romkin   (2004-06-24 11:28:00) [33]

Кстати, насколько я понял, тебе значение строки не нужно? Тогда StrToInt64, но разбей строку на две половины - как раз влезет.
Может, все-таки скажешь, что у процедуры на входе и что нужно получить на выходе?


Fay   (2004-06-24 11:27:00) [34]

2Romkin ©   (24.06.04 11:21) [50]
К тому же, код [45] не годится для string 8)


Romkin   (2004-06-24 11:21:00) [35]

Не надо беспокоиться, думаю, DelSpaces в моей редакции уже перестала быть узким местом.
Простой пример: допустим, есть программа, и одна функция в ней отнимает 4% времени обработки. Ускорив эту функцию в два раза, вы получите уменьшение времени... всего на 2%.
ЛУчше посмотреть на другие участки программы...
А еще лучше воспользоваться профилировщиком


Кастуся   (2004-06-24 11:09:00) [36]


> www.shegeda.by.ru   (24.06.04 09:48) [45]

твой алгоритм не работает. Я его в процедуру пихаю:
procedure DelSpaces(var S: String);
var
NewLength : integer;
begin
asm
  mov edx, s
  mov ebx, s
  jmp @@NextChar
@@NextChar:
  mov al, [ebx]
  inc ebx
  or  al, al
  jz  @@StrEnd
  cmp al, ' '
  je  @@NextChar
@@CopyChar:
  mov [edx], al
  inc edx
  jmp @@NextChar
@@StrEnd:
  mov [edx], al
  sub edx, s
  mov NewLength, edx
end;
SetLength(s,NewLength);
end;

> www.shegeda.by.ru   (24.06.04 09:58) [47]
> Это во-первых...
> Во вторых, нужно ли чтение файла?

когда я закомментировал всю обработку строк, а отавил только чтение стандартным методом:
while not eof(f) do
readln(f,st);

то мой файл в 8Мб прочитывает за 0.4с. Впечатляет? Так что с этим проблем нету.

А вообще, чего я уже добился с момента начала этой ветки, меня впечатляет! Скорость обработки увеличилась раза в 4-5!!!


  (2004-06-24 10:00:00) [37]

Удалено модератором


  (2004-06-24 09:58:00) [38]

Удалено модератором


Fay   (2004-06-24 09:51:00) [39]

2www.shegeda.by.ru   (24.06.04 09:48) [45]
Какой выигрыш?


  (2004-06-24 09:48:00) [40]

Удалено модератором


Страницы:   1 2 3 4 5

Наверх

Титульная страница Поиск, карта сайта Написать письмо