Why is the result of concatenating the following paths /c/d
?
std::filesystem::path{"/a"} / std::filesystem::path{"b"} / std::filesystem::path{"/c/d"}
My mental model so far had the resulting path set to /a/b/c/d
. To my surprise, it was simply /c/d
. Curious to know where I went wrong here. (And what the right mental model is)
CodePudding user response:
/a
is an absolute path, and b
is a relative path, so concatenating them will produce /a/b
.
But /c/d
is also an absolute path, so concatenating it with anything in front of it is basically a no-op, the absolute path will take priority, so the final result is just /c/d
.
This is discussed in more detail on cppreference.com:
std::filesystem::operator/(std::filesystem::path)
Concatenates two path components using the preferred directory separator if appropriate (see operator/= for details).
Effectively returns
path(lhs) /= rhs
.
std::filesystem::path::operator/=
path& operator/=( const path& p );
If
p.is_absolute() || (p.has_root_name() && p.root_name() != root_name())
, then replaces the current path with p as if byoperator=(p)
and finishes.
To get the result you want, drop the leading /
from /c/d
to make it a relative path:
std::filesystem::path{"/a"} / std::filesystem::path{"b"} / std::filesystem::path{"c/d"}
CodePudding user response:
what the right mental model is
a / b
means "if b
is not absolute, then it's relative to a
".
This lets you have a "default" base directory, where the rhs is assumed to be located, if the path is not absolute.