开发者

boost::filesystem::rename: Cannot create a file when that file already exists

I'm renaming a file using boost::filesystem, and so开发者_如何学Cmetimes the target file will exist. According to the boost documentation here:

http://www.boost.org/doc/libs/1_42_0/libs/filesystem/doc/reference.html#Non-member-functions

template void rename(const Path1& from_p, const Path2& to_p); Requires: Path1::external_string_type and Path2::external_string_type are the same type.

Effects: Renames from_p to to_p, as if by POSIX rename().

Postconditions: !exists(from_p) && exists(to_p), and the contents and attributes of the file originally named from_p are otherwise unchanged.

[Note: If from_p and to_p resolve to the same file, no action is taken. Otherwise, if to_p resolves to an existing file, it is removed. A symbolic link is itself renamed, rather than the file it resolves to being renamed. -- end note]

(my emphasis)

When testing this code compiled via MS Visual Studio 2008 on XP SP3, the rename throws boost::filesystem::filesystem_error with the message:

Cannot create a file when that file already exists

I note this has been raised in a bug report: https://svn.boost.org/trac/boost/ticket/2866

... but claims to be closed in Boost 1.41.0 and I'm using Boost 1.42.0.

Am I doing something wrong here or should I just revert to std::rename?

I haven't tested this on Linux yet so don't know if the problem exists there too.


Looks like it was fixed, but only in the sandbox "V3" version of Boost.Filesystem, which is not in the mainline Boost releases yet.

I tested on Boost 1.43.0 on Linux with the same results - in fact the bug report points out the offending code, which explicitly checks for existence on POSIX and throws the exception. It's possible this was done originally because MoveFile on Windows exhibits the same behavior? In the sandbox V3 version, rename will call MoveFileEx on Windows and std::rename on POSIX, and allows overwriting an existing file.

I suppose you could work around it by calling boost::filesystem::remove on the target before calling boost::filesystem::rename, depending upon whether your program needs the operation to be atomic or not.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜