Наши проекты:
Журнал · Discuz!ML · Wiki · DRKB · Помощь проекту |
||
ПРАВИЛА | FAQ | Помощь | Поиск | Участники | Календарь | Избранное | RSS |
[3.144.18.4] |
|
Сообщ.
#1
,
|
|
|
ЛЮди подскажите.
Есть такая проблема: Нужно узнать размер файла. Использовал... function GetFileSize(FileName: String): Integer; var FS: TFileStream; begin try FS := TFileStream.Create(Filename, fmOpenRead); except Result := -1; end; if Result <> -1 then Result := FS.Size; FS.Free; end; procedure TForm1.FormCreate(Sender: TObject); begin ShowMessage(IntToStr(GetFileSize('c:\prova.pdf'))); end; Но этот код не работает, если файл используется другим приложением. Подскажите, как узнать размер, если файл используется в данный момент. |
Сообщ.
#2
,
|
|
|
function GetFileSize(FileName: String): Integer; var FS: TFileStream; begin try FS := TFileStream.Create(Filename, fmOpenRead or fmShareDenyWrite); except Result := -1; end; if Result <> -1 then Result := FS.Size; FS.Free; end; procedure TForm1.FormCreate(Sender: TObject); begin ShowMessage(IntToStr(GetFileSize('c:\prova.pdf'))); end; |
Сообщ.
#3
,
|
|
|
function GetFSize(const fName: string): Integer; var w32fd: WIN32_FIND_DATA; find_h: DWORD; begin find_h:=FindFirstFile(PChar(fName), w32fd); if find_h<>INVALID_HANDLE_VALUE then Result:=w32fd.nFileSizeLow else Result:=-1; Windows.FindClose(find_h); end; Добавлено Rrader твой способ не будет работать с открытыми файлами. |
Сообщ.
#4
,
|
|
|
Цитата Ct757 @ Rrader твой способ не будет работать с открытыми файлами. Более того. И у Rrader, и у GreySkil есть серьезная ошибка в коде. Если TFileStream.Create пройдет без ошибки, то на момент проверки if Result <> -1, значение Result не определено. И поведение программы будет вообще не предсказуемым. Кстати, об этом должен был предупредить компилятор. Или у вас отключены проедупреждения? |
Сообщ.
#5
,
|
|
|
function FileSize(const FileName: String): Cardinal; var FileHandle: THandle; begin try FileHandle := CreateFile(PChar(FileName), GENERIC_READ, FILE_SHARE_READ, nil, OPEN_EXISTING, FILE_ATTRIBUTE_ARCHIVE, 0); try Result := GetFileSize(FileHandle, nil); finally CloseHandle(FileHandle); end; except raise Exception.Create('Oops! Can''t get file size :('); end; end; |
Сообщ.
#6
,
|
|
|
to Domino твой код даст ошибку если файл открыт другой программой.
Правильный способ, лишенный этого недостатка, уже приведен Ct757'ом. Правда он возвращает 32-х битную величину. Т.е. применима только к файлам, размер которых не превышает 4Гб. Современные файловые системы (NTFS) допускаю размеры файлов более 4 Гб (64 бита). Вот вариант который позволяет работать с такими файлами: function FileSize (FileName :String) :Int64; var Handle: tHandle; FindData: tWin32FindData; begin Handle := FindFirstFile(PChar(FileName), FindData); if Handle = INVALID_HANDLE_VALUE then SysUtils.RaiseLastOSError; Windows.FindClose(Handle); if (FindData.dwFileAttributes and FILE_ATTRIBUTE_DIRECTORY) <> 0 then Result := 0 // Размер каталога всегда считаем равным 0 else begin SysUtils.Int64Rec(Result).Hi := FindData.nFileSizeHigh; SysUtils.Int64Rec(Result).Lo := FindData.nFileSizeLow; end; end; |