std::filesystem::path::lexically_normal, std::filesystem::path::lexically_relative, std::filesystem::path::lexically_proximate

来自cppreference.com
< cpp‎ | filesystem‎ | path
 
 
 
 
path lexically_normal() const;
(1) (C++17 起)
path lexically_relative( const path& base ) const;
(2) (C++17 起)
path lexically_proximate( const path& base ) const;
(3) (C++17 起)
1) 返回以其通用格式转换成正规形式的 *this。
2) 返回设为相对于 base 的 *this。
  • 首先,若 root_name() != base.root_name() 为 true 或 is_absolute() != base.is_absolute() 为 true 或 (!has_root_directory() && base.has_root_directory()) 为 true 或 relative_path() 或 base.relative_path() 中的任何文件名能转译为 根名,则返回默认构造的 path。
  • 否则,首先确定 *this 和 base 的首个不匹配元素,如同以 auto [a, b] = mismatch(begin(), end(), base.begin(), base.end()),然后
  • 若 a == end() 且 b == base.end(),则返回 path(".");
  • 否则,定义 N 为 [b, base.end()) 中既非 点 亦非 点点 的非空文件名元素数减去 点点 文件名元素数。若 N < 0 则返回默认构造的 path,
  • 否则,若 N = 0 且 a == end() || a->empty(),则返回 path("."),
  • 否则返回由以下方式合成的对象
  • 默认构造 path() 后
  • 应用 N 次 operator/=(path("..")),之后
  • 对半开范围 [a, end()) 中的每个元素应用一次 operator/=
3) 若 lexically_relative(base) 的值不是空路径,则返回它。否则返回 *this。

参数

(无)

返回值

1) 路径的正规形式。
2) 路径的相对形式。
3) 路径的近似形式。

异常

可能会抛出由实现定义的异常。

注解

这些转换是纯词法的。它们不检查路径是否存在,不跟随符号链接,且完全不访问文件系统。关于 lexically_relative 与 lexically_proximate 跟随符号链接的对应版本,见 relative 与 proximate。

Windows 上返回路径拥有反斜杠(偏好分隔符)。

POSIX 上相对路径中的文件名均不可接受为 根名 。

示例

#include <cassert>
#include <filesystem>
#include <iostream>
namespace fs = std::filesystem;
 
int main()
{
    assert(fs::path("a/./b/..").lexically_normal() == "a/");
    assert(fs::path("a/.///b/../").lexically_normal() == "a/");
    assert(fs::path("/a/d").lexically_relative("/a/b/c") == "../../d");
    assert(fs::path("/a/b/c").lexically_relative("/a/d") == "../b/c");
    assert(fs::path("a/b/c").lexically_relative("a") == "b/c");
    assert(fs::path("a/b/c").lexically_relative("a/b/c/x/y") == "../..");
    assert(fs::path("a/b/c").lexically_relative("a/b/c") == ".");
    assert(fs::path("a/b").lexically_relative("c/d") == "../../a/b");
    assert(fs::path("a/b").lexically_relative("/a/b") == "");
    assert(fs::path("a/b").lexically_proximate("/a/b") == "a/b");
}

缺陷报告

下列更改行为的缺陷报告追溯地应用于以前出版的 C++ 标准。

缺陷报告 应用于 出版时的行为 正确行为
LWG 3070 C++17 亦能为根名的文件名可能导致诧异的结果 当作错误情况
LWG 3096 C++17 错误地处理了尾随 "/" 和 "/." 已更正

参阅

组成一个相对路径
(函数)