Вам следует позвонить GetFileSizeEx
, который проще в использовании, чем более старый GetFileSize
. Вам нужно будет открыть файл, позвонив по номеру CreateFile
, но это дешевая операция. Ваше предположение, что открытие файла дорого, даже файл размером 12 ГБ, неверно.
Вы можете использовать следующую функцию для выполнения работы:
__int64 FileSize(const wchar_t* name)
{
HANDLE hFile = CreateFile(name, GENERIC_READ,
FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL, NULL);
if (hFile==INVALID_HANDLE_VALUE)
return -1; // error condition, could call GetLastError to find out more
LARGE_INTEGER size;
if (!GetFileSizeEx(hFile, &size))
{
CloseHandle(hFile);
return -1; // error condition, could call GetLastError to find out more
}
CloseHandle(hFile);
return size.QuadPart;
}
Существуют другие вызовы API, которые возвращают вам размер файла, не заставляя вас создавать дескриптор файла, в частности GetFileAttributesEx
. Однако вполне вероятно, что эта функция просто откроет файл за кулисами.
__int64 FileSize(const wchar_t* name)
{
WIN32_FILE_ATTRIBUTE_DATA fad;
if (!GetFileAttributesEx(name, GetFileExInfoStandard, &fad))
return -1; // error condition, could call GetLastError to find out more
LARGE_INTEGER size;
size.HighPart = fad.nFileSizeHigh;
size.LowPart = fad.nFileSizeLow;
return size.QuadPart;
}
Если вы компилируете с Visual Studio и хотите избежать вызова Win32 API, тогда вы можете использовать _wstat64
.
Вот _wstat64
версия функции на основе:
__int64 FileSize(const wchar_t* name)
{
__stat64 buf;
if (_wstat64(name, &buf) != 0)
return -1; // error, could use errno to find out more
return buf.st_size;
}
Если производительность когда-либо становилась проблемой для вас, то вам нужно рассчитать различные варианты на всех платформах, на которые вы ориентируетесь, чтобы принять решение. Не думайте, что API, которые не требуют, чтобы вы вызывали CreateFile
, были быстрее. Они могут быть, но вы не узнаете, пока не рассчитаете время.