From 4ecf386cdad3ff098034b5e28333ad57cca817ff Mon Sep 17 00:00:00 2001 From: "Dirk-Jan C. Binnema" Date: Sun, 6 Aug 2023 12:58:02 +0300 Subject: [PATCH] utils-file: don't use regexp in join_paths It's slow. --- lib/utils/mu-utils-file.hh | 32 +++++++++++++++++++++++++++----- 1 file changed, 27 insertions(+), 5 deletions(-) diff --git a/lib/utils/mu-utils-file.hh b/lib/utils/mu-utils-file.hh index 9f429bd7..8edebcbc 100644 --- a/lib/utils/mu-utils-file.hh +++ b/lib/utils/mu-utils-file.hh @@ -157,16 +157,38 @@ std::string runtime_path(RuntimePath path, const std::string& muhome=""); * @return the path */ static inline std::string join_paths() { return {}; } -template -std::string join_paths(S&& s, Args...args) { +template std::string join_paths_(S&& s) { return std::string{s}; } +template +std::string join_paths_(S&& s, Args...args) { static std::string sepa{"/"}; auto&& str{std::string{std::forward(s)}}; - if (auto&& rest{join_paths(std::forward(args)...)}; !rest.empty()) + if (auto&& rest{join_paths_(std::forward(args)...)}; !rest.empty()) str += (sepa + rest); + return str; +} - static auto rx = Regex::make("//*").value(); - return rx.replace(str, sepa); +template +std::string join_paths(S&& s, Args...args) { + + constexpr auto sepa = '/'; + auto path = join_paths_(std::forward(s), std::forward(args)...); + + auto c{0U}; + while (c < path.size()) { + + if (path[c] != sepa) { + ++c; + continue; + } + + while (path[++c] == '/') { + path.erase(c, 1); + --c; + } + } + + return path; }