在一个Windows应用程序中,我有一个类来封装文件名和缓冲区。你可以使用文件名构造它,并且可以查询对象以查看缓冲区是否已填充,如果没有则返回nullptr,如果已经填充则返回缓冲区地址。当对象超出范围时,缓冲区会被释放:
class file_buffer
{
public:
file_buffer(const std::string& file_name);
~file_buffer();
void* buffer();
private:
...
}
我希望异步地将数据放入内存,据我所见,有两个选择:创建一个缓冲区并通过ReadFileEx使用重叠I/O,或者使用MapViewOfFile在另一个线程中访问地址。目前,我正在使用ReadFileEx,但存在一些问题,请求大于16MB时易发生故障:我可以尝试拆分请求,但会出现同步问题;如果IO未完成即对象已超出范围,则会出现缓冲清除问题。此外,如果快速连续创建类的多个实例,事情会变得非常棘手。映射并在另一个线程上触摸数据似乎要简单得多,因为我不会有上限问题:而且,如果客户端绝对需要立即获得数据,则可以直接引用地址,让操作系统处理页面故障并采取阻塞操作。这个应用程序需要支持单核机器,因此我的问题是:在另一个软件线程上的页面故障是否比当前线程上的重叠I/O更昂贵?它们会使进程停止吗?重叠I/O是否以同样的方式使进程停止,还是有些我不理解的操作系统魔力?页面故障是否仍然使用重叠I/O执行?我已经好好阅读了这些主题:http://msdn.microsoft.com/en-us/library/aa365199(v=vs.85).aspx(文件管理中的I/O概念)http://msdn.microsoft.com/en-us/library/windows/desktop/aa366556(v=vs.85).aspx(文件映射),但我似乎无法推断出如何进行性能权衡。