我想创build一个可以被ifstream
打开的文件。
我知道使用Windows API时很容易: CreateFile
CreateFile(...,FILE_SHARE_DELETE,...)
但是,当我testing与ifstream打开文件。
打开时不能删除。
我没有find关于在ifstream
上设置像FILE_SHARE_DELETE
这样的属性的任何文档。
我该如何解决这个问题呢?
文件权限因操作系统而异:
全文访问共享,用于读取,写入或删除
在父目录上写入+执行权限。 文件本身的权限是不相关的
由于Windows实际上是唯一具有删除访问权限的系统,并且已经以CreateFile
和FILE_SHARE_DELETE
的形式提供了自己的访问FILE_SHARE_DELETE
,所以实际上并没有动力去标准化这个功能。
如果这个功能对你的程序来说很重要,你可以实现这个跨平台的功能(注意,根据文件的大小,这可能会非常昂贵):
fstream
打开文件进行读写; 如果这个失败了,别的东西就会锁定在文件上,并且不能打开它进行删除 close
文件 remove
文件; 如果失败,则不具有文件的删除权限 ofstream
只要返回的流是开放的,操作系统负责防止对文件权限的更改或者包含目录。 因此,由于您已经删除了文件,因此您可以在关闭文件流后仍然可以删除文件。
Visual Studio的std::ifstream
版本有一个非标准的构造函数和一个非标准的open()
重载,它们都有一个额外的可选_Prot
参数来指定“文件保护/共享标志”(参见_fsopen()
标志)。 但是, delete
共享不是支持的标志之一。
不过,还有一个选择。 Visual Studio版本的std::ifstream
和std::ofstream
都有非标准的构造函数,它们接受文件访问的FILE*
。 例如,您可以使用Microsoft的_open_osfhandle()
和_fdopen()
函数将CreateFile()
的HANDLE
封装到FILE*
(为简洁起见,删除了错误处理):
我可以使用CreateFile,但强制句柄到一个std :: ofstream?
HANDLE file_handle = CreateFile(...,FILE_SHARE_DELETE,...); int file_descriptor = _open_osfhandle((intptr_t)file_handle, _O_RDONLY); FILE* file = _fdopen(file_descriptor, "r"); std::ifstream stream(file); ... // Closes stream, file, file_descriptor, and file_handle. stream.close();
如果你需要一些更适合非微软编译器的可移植的东西,你可能不得不写一个自定义的std::basic_streambuf
类(或者从std::filebuf
派生)来包装你的HANDLE
,然后传递这个类的一个对象直接到std::basic_istream
构造函数。