From 1741e90dec69ba8004530e837b35caa1e75af690 Mon Sep 17 00:00:00 2001 From: Victor Zverovich Date: Sat, 18 Feb 2023 09:39:58 -0800 Subject: [PATCH] Always call parse in range formatter --- include/fmt/ranges.h | 24 ++++++++++++------------ test/ranges-test.cc | 17 ++++++++++------- 2 files changed, 22 insertions(+), 19 deletions(-) diff --git a/include/fmt/ranges.h b/include/fmt/ranges.h index 8912fe93..755f49df 100644 --- a/include/fmt/ranges.h +++ b/include/fmt/ranges.h @@ -235,7 +235,7 @@ void for_each(index_sequence, Tuple&& tup, F&& f) noexcept { } template -FMT_CONSTEXPR auto get_indexes(T const&) +FMT_CONSTEXPR auto get_indexes(const T&) -> make_index_sequence::value> { return {}; } @@ -361,7 +361,7 @@ struct formatter + template auto format(const Tuple& value, FormatContext& ctx) const -> decltype(ctx.out()) { auto out = detail::copy_str(opening_bracket_, ctx.out()); @@ -437,13 +437,13 @@ struct range_formatter< basic_string_view closing_bracket_ = detail::string_literal{}; - template + template FMT_CONSTEXPR static auto maybe_set_debug_format(U& u, bool set) -> decltype(u.set_debug_format(set)) { u.set_debug_format(set); } - template + template FMT_CONSTEXPR static void maybe_set_debug_format(U&, ...) {} FMT_CONSTEXPR void maybe_set_debug_format(bool set) { @@ -451,7 +451,7 @@ struct range_formatter< } public: - FMT_CONSTEXPR range_formatter() { maybe_set_debug_format(true); } + FMT_CONSTEXPR range_formatter() {} FMT_CONSTEXPR auto underlying() -> detail::range_formatter_type& { return underlying_; @@ -477,14 +477,14 @@ struct range_formatter< ++it; } - if (it == end || *it == '}') return it; + if (it != end && *it != '}') { + if (*it != ':') FMT_THROW(format_error("invalid format specifier")); + custom_specs_ = true; + ++it; + } else { + maybe_set_debug_format(true); + } - if (*it != ':') - FMT_THROW(format_error("no other top-level range formatters supported")); - - maybe_set_debug_format(false); - custom_specs_ = true; - ++it; ctx.advance_to(it); return underlying_.parse(ctx); } diff --git a/test/ranges-test.cc b/test/ranges-test.cc index 26e3362a..29ec401a 100644 --- a/test/ranges-test.cc +++ b/test/ranges-test.cc @@ -366,7 +366,7 @@ TEST(ranges_test, is_printable) { EXPECT_FALSE(is_printable(0x110000)); } -TEST(ranges_test, escape_string) { +TEST(ranges_test, escape) { using vec = std::vector; EXPECT_EQ(fmt::format("{}", vec{"\n\r\t\"\\"}), "[\"\\n\\r\\t\\\"\\\\\"]"); EXPECT_EQ(fmt::format("{}", vec{"\x07"}), "[\"\\x07\"]"); @@ -386,8 +386,11 @@ TEST(ranges_test, escape_string) { "[\"\\xf0(\\x00\\x00anything\"]"); // Correct utf-8. - EXPECT_EQ(fmt::format("{}", vec{"понедельник"}), "[\"понедельник\"]"); + EXPECT_EQ(fmt::format("{}", vec{"🦄"}), "[\"🦄\"]"); } + + EXPECT_EQ(fmt::format("{}", std::vector>{{'x'}}), + "[['x']]"); } template struct fmt_ref_view { @@ -420,7 +423,7 @@ TEST(ranges_test, container_adaptor) { } { - std::stack s; + auto s = std::stack(); s.push(1); s.push(2); EXPECT_EQ(fmt::format("{}", s), "[1, 2]"); @@ -428,14 +431,14 @@ TEST(ranges_test, container_adaptor) { } { - std::queue q; + auto q = std::queue(); q.push(1); q.push(2); EXPECT_EQ(fmt::format("{}", q), "[1, 2]"); } { - std::priority_queue q; + auto q = std::priority_queue(); q.push(3); q.push(1); q.push(2); @@ -444,7 +447,7 @@ TEST(ranges_test, container_adaptor) { } { - std::stack s; + auto s = std::stack(); s.push('a'); s.push('b'); // See https://cplusplus.github.io/LWG/issue3881. @@ -461,7 +464,7 @@ TEST(ranges_test, container_adaptor) { container_type c; }; - my_container_adaptor m; + auto m = my_container_adaptor(); m.push(1); m.push(2); EXPECT_EQ(fmt::format("{}", m), "[1, 2]");