用MapViewOfFile处理大文件-内存不足(转帖学习)
2010-09-28 15:57
459 查看
用MapViewOfFile处理大文件时,如果文件过大,如400M,则无法一次性映射入内存,否则会出现1132错误,即内存不足。原因可能为操作系统无法找到连续的内存。因此需要通过分页的方式,逐页将文件内容映射到内存。
相关资料:
LPVOID
MapViewOfFile(HANDLE hFileMappingObject,
DWORD dwDesiredAccess,
DWORD dwFileOffsetHigh,
DWORD dwFileOffsetLow,
DWORD dwNumberOfBytesToMap);
MapViewOfFile()函数负责把文件数据映射到进程的地址空间,参数hFileMappingObject为
CreateFileMapping()返回的文件映像对象句柄。参数dwDesiredAccess则再次指定了对文件数据的访问方式,而且同样要与
CreateFileMapping()函数所设置的保护属性相匹配。虽然这里一再对保护属性进行重复设置看似多余,但却可以使应用程序能更多的对数据的保护属性实行有效控制。MapViewOfFile()函数允许全部或部分映射文件,在映射时,需要指定数据文件的偏移地址以及待映射的长度。其中,文件的偏移地址由DWORD型的参数dwFileOffsetHigh和dwFileOffsetLow组成的64位值来指定,而且必须是操作系统的分配粒度的整数倍,对于Windows操作系统,分配粒度固定为64KB。当然,也可以通过如下代码来动态获取当前操作系统的分配粒度:
SYSTEM_INFO sinf;
GetSystemInfo(&sinf);
DWORD dwAllocationGranularity = sinf.dwAllocationGranularity;
参数dwNumberOfBytesToMap指定了数据文件的映射长度,这里需要特别指出的是,对于Windows
9x操作系统,如果MapViewOfFile()无法找到足够大的区域来存放整个文件映射对象,将返回空值(NULL);但是在Windows
2000下,MapViewOfFile()只需要为必要的视图找到足够大的一个区域即可,而无须考虑整个文件映射对象的大小。
由此看出,分页映射文件时,每页的起始位置startpos,必须为64K的整数倍。
HANDLE
hFile=::CreateFile("c://111.dwf",GENERIC_READ,FILE_SHARE_READ |
FILE_SHARE_WRITE,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_READONLY,NULL);
////////////////////////////////////////////////////////////////////
//
CreateFileMapping 的dwMaximumsize必须设置为0,否则MapViewOfFile中offset>0时,映射失败
HANDLE
m_hCurFileMap =
CreateFileMapping
( hFile, NULL, PAGE_READONLY, 0, 0, NULL );
DWORD offset=64*1024;
LPVOID
m_pReadBuffer=MapViewOfFile(m_hCurFileMap,FILE_MAP_READ,
(DWORD)0,
(DWORD)(offset &
0xFFFFFFFF),
offset
);
相关资料:
LPVOID
MapViewOfFile(HANDLE hFileMappingObject,
DWORD dwDesiredAccess,
DWORD dwFileOffsetHigh,
DWORD dwFileOffsetLow,
DWORD dwNumberOfBytesToMap);
MapViewOfFile()函数负责把文件数据映射到进程的地址空间,参数hFileMappingObject为
CreateFileMapping()返回的文件映像对象句柄。参数dwDesiredAccess则再次指定了对文件数据的访问方式,而且同样要与
CreateFileMapping()函数所设置的保护属性相匹配。虽然这里一再对保护属性进行重复设置看似多余,但却可以使应用程序能更多的对数据的保护属性实行有效控制。MapViewOfFile()函数允许全部或部分映射文件,在映射时,需要指定数据文件的偏移地址以及待映射的长度。其中,文件的偏移地址由DWORD型的参数dwFileOffsetHigh和dwFileOffsetLow组成的64位值来指定,而且必须是操作系统的分配粒度的整数倍,对于Windows操作系统,分配粒度固定为64KB。当然,也可以通过如下代码来动态获取当前操作系统的分配粒度:
SYSTEM_INFO sinf;
GetSystemInfo(&sinf);
DWORD dwAllocationGranularity = sinf.dwAllocationGranularity;
参数dwNumberOfBytesToMap指定了数据文件的映射长度,这里需要特别指出的是,对于Windows
9x操作系统,如果MapViewOfFile()无法找到足够大的区域来存放整个文件映射对象,将返回空值(NULL);但是在Windows
2000下,MapViewOfFile()只需要为必要的视图找到足够大的一个区域即可,而无须考虑整个文件映射对象的大小。
由此看出,分页映射文件时,每页的起始位置startpos,必须为64K的整数倍。
HANDLE
hFile=::CreateFile("c://111.dwf",GENERIC_READ,FILE_SHARE_READ |
FILE_SHARE_WRITE,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_READONLY,NULL);
////////////////////////////////////////////////////////////////////
//
CreateFileMapping 的dwMaximumsize必须设置为0,否则MapViewOfFile中offset>0时,映射失败
HANDLE
m_hCurFileMap =
CreateFileMapping
( hFile, NULL, PAGE_READONLY, 0, 0, NULL );
DWORD offset=64*1024;
LPVOID
m_pReadBuffer=MapViewOfFile(m_hCurFileMap,FILE_MAP_READ,
(DWORD)0,
(DWORD)(offset &
0xFFFFFFFF),
offset
);
相关文章推荐
- 用MapViewOfFile处理大文件-内存不足
- (转)mapViewOfFile内存文件读写
- [zz]内存映射文件,UnmapViewOfFile/MapViewOfFile(转载)
- 内存映射文件,UnmapViewOfFile/MapViewOfFile(转载)
- Windows环境下利用“共享内存”实现进程间通信的C/C++代码---利用CreateFileMapping和MapViewOfFile
- CreateFileMapping, MapViewOfFile 实现文件共享
- Windows API学习(一)MapViewOfFile后一定要UnMapViewOfFile
- [转]Windows环境下利用“共享内存”实现进程间通信的C/C++代码---利用CreateFileMapping和MapViewOfFile
- Windows环境下利用“共享内存”实现进程间通信的C/C++代码---利用CreateFileMapping和MapViewOfFile
- CreateFileMapping, MapViewOfFile 实现文件共享
- c++中共享内存操作函数MapViewOfFile解析(二)
- 使用文件映射的方式进行共享数据中CreateFileMapping、MapViewOfFile函数参数说明
- Android学习之实现WebView中input="file"选择文件,处理选择图片无法返回类型问题
- 关于使用MAPVIEWOFFILE大文件的读写(DELPHI版)
- Windows环境下利用“共享内存”实现进程间通信的C/C++代码---利用CreateFileMapping和MapViewOfFile
- 共享内存对象方法(MapViewOfFile)
- CreateFileMapping, MapViewOfFile 实现文件共享 (.net4.0 built-in)
- FileReference.Load 加载时,文件过大,IE内核浏览器会报:Error: Error #1000: 系统内存不足。
- MapViewOfFile 内存泄露
- System.Drawing.Image.FromFile()处理图片,内存不足错误