diff options
author | Max Kellermann <max@musicpd.org> | 2020-04-03 19:05:40 +0200 |
---|---|---|
committer | Max Kellermann <max@musicpd.org> | 2020-04-03 19:45:01 +0200 |
commit | 0080eee857f1c93caae1a878031874a16f28bf21 (patch) | |
tree | 9340be33360f8028f00705a10565d0ee3c681b4d /src/fs | |
parent | 2429cc8778d602ed8a93882a81111b5603fd4b17 (diff) |
fs/Traits: add Relative() overload with std::string_view
Diffstat (limited to 'src/fs')
-rw-r--r-- | src/fs/Traits.cxx | 43 | ||||
-rw-r--r-- | src/fs/Traits.hxx | 6 |
2 files changed, 49 insertions, 0 deletions
diff --git a/src/fs/Traits.cxx b/src/fs/Traits.cxx index fbd87bdce..3c596dfc8 100644 --- a/src/fs/Traits.cxx +++ b/src/fs/Traits.cxx @@ -117,6 +117,37 @@ RelativePathImpl(typename Traits::string_view base, return other; } +template<typename Traits> +typename Traits::string_view +RelativePathImpl(typename Traits::string_view base, + typename Traits::string_view _other) noexcept +{ + BasicStringView<typename Traits::value_type> other(_other); + + if (!other.SkipPrefix(base)) + /* mismatch */ + return {}; + + if (!other.empty()) { + if (!Traits::IsSeparator(other.front())) { + if (!base.empty() && Traits::IsSeparator(other.data[-1])) + /* "other" has no more slash, but the + matching base ended with a slash: + enough to detect a match */ + return other; + + /* mismatch */ + return {}; + } + + /* skip remaining path separators */ + while (!other.empty() && Traits::IsSeparator(other.front())) + other.pop_front(); + } + + return other; +} + PathTraitsFS::string PathTraitsFS::Build(string_view a, string_view b) noexcept { @@ -141,6 +172,12 @@ PathTraitsFS::Relative(string_view base, const_pointer other) noexcept return RelativePathImpl<PathTraitsFS>(base, other); } +PathTraitsFS::string_view +PathTraitsFS::Relative(string_view base, string_view other) noexcept +{ + return RelativePathImpl<PathTraitsFS>(base, other); +} + PathTraitsFS::string PathTraitsFS::Apply(const_pointer base, const_pointer path) noexcept { @@ -178,3 +215,9 @@ PathTraitsUTF8::Relative(string_view base, const_pointer other) noexcept { return RelativePathImpl<PathTraitsUTF8>(base, other); } + +PathTraitsUTF8::string_view +PathTraitsUTF8::Relative(string_view base, string_view other) noexcept +{ + return RelativePathImpl<PathTraitsUTF8>(base, other); +} diff --git a/src/fs/Traits.hxx b/src/fs/Traits.hxx index d2e5f83b0..bcb432f60 100644 --- a/src/fs/Traits.hxx +++ b/src/fs/Traits.hxx @@ -149,6 +149,9 @@ struct PathTraitsFS { gcc_pure gcc_nonnull_all static const_pointer Relative(string_view base, const_pointer other) noexcept; + gcc_pure + static string_view Relative(string_view base, string_view other) noexcept; + /** * Constructs the path from the given components. * If either of the components is empty string, @@ -257,6 +260,9 @@ struct PathTraitsUTF8 { gcc_pure gcc_nonnull_all static const_pointer Relative(string_view base, const_pointer other) noexcept; + gcc_pure + static string_view Relative(string_view base, string_view other) noexcept; + /** * Constructs the path from the given components. * If either of the components is empty string, |