Skip to content

Commit

Permalink
Simplify how we stringify strings and return "nullptr" in more cases
Browse files Browse the repository at this point in the history
  • Loading branch information
jimporter committed May 3, 2024
1 parent 6633422 commit 2da2fc0
Show file tree
Hide file tree
Showing 3 changed files with 40 additions and 59 deletions.
21 changes: 12 additions & 9 deletions include/mettle/output/string.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -33,15 +33,6 @@ namespace mettle {
}
}

template<typename Char = char, typename Traits = std::char_traits<Char>,
typename Alloc = std::allocator<Char>>
std::basic_string<Char, Traits, Alloc>
null_str() {
std::basic_ostringstream<Char, Traits, Alloc> ss;
ss << static_cast<const void *>(nullptr);
return ss.str();
}

}

template<typename Char, typename Traits,
Expand Down Expand Up @@ -80,6 +71,18 @@ namespace mettle {
return s;
}

inline std::string_view
string_convert(const std::basic_string_view<unsigned char> &s) {
auto begin = reinterpret_cast<const char *>(s.data());
return std::string_view(begin, s.size());
}

inline std::string_view
string_convert(const std::basic_string_view<signed char> &s) {
auto begin = reinterpret_cast<const char *>(s.data());
return std::string_view(begin, s.size());
}

// Ignore warnings about deprecated <codecvt>.
#if defined(_MSC_VER) && !defined(__clang__)
# pragma warning(push)
Expand Down
52 changes: 18 additions & 34 deletions include/mettle/output/to_printable.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -61,41 +61,12 @@ namespace mettle {
return escape_string(string_convert(std::u32string(1, c)), '\'');
}

inline std::string to_printable(const char *s) {
if(!s) return detail::null_str();
return escape_string(s);
}

inline std::string to_printable(const unsigned char *s) {
if(!s) return detail::null_str();
return escape_string(reinterpret_cast<const char*>(s));
}

inline std::string to_printable(const signed char *s) {
if(!s) return detail::null_str();
return escape_string(reinterpret_cast<const char*>(s));
}

inline std::string to_printable(const wchar_t *s) {
if(!s) return detail::null_str();
return escape_string(string_convert(s));
}

inline std::string to_printable(const char16_t *s) {
if(!s) return detail::null_str();
return escape_string(string_convert(s));
}

inline std::string to_printable(const char32_t *s) {
if(!s) return detail::null_str();
return escape_string(string_convert(s));
}

template<typename T>
inline auto to_printable(T *t) -> std::enable_if_t<
inline auto to_printable(const T *s) -> std::enable_if_t<
is_any_char_v<T>, std::string
> {
return to_printable(const_cast<const T *>(t));
if(!s) return to_printable(nullptr);
return escape_string(string_convert(s));
}

template<typename Ret, typename ...Args>
Expand All @@ -121,7 +92,7 @@ namespace mettle {
}

template<typename T, std::size_t N>
auto to_printable(T (&v)[N]) -> std::enable_if_t<
auto to_printable(const T (&v)[N]) -> std::enable_if_t<
!is_any_char_v<T>, std::string
> {
return to_printable(std::begin(v), std::end(v));
Expand All @@ -133,7 +104,15 @@ namespace mettle {

template<typename T>
inline auto to_printable(const T &t) {
if constexpr(std::is_enum_v<T>) {
if constexpr(std::is_pointer_v<T>) {
using ValueType = std::remove_pointer_t<T>;
if constexpr(!std::is_const_v<ValueType>) {
return to_printable(const_cast<const ValueType*>(t));
} else {
if(!t) return to_printable(nullptr);
return (std::ostringstream{} << t).str();
}
} else if constexpr(std::is_enum_v<T>) {
return type_name<T>() + "(" + std::to_string(
static_cast<typename std::underlying_type<T>::type>(t)
) + ")";
Expand All @@ -152,6 +131,11 @@ namespace mettle {
}
}

template<typename T>
inline auto to_printable(const volatile T &t) {
return to_printable(const_cast<const T &>(t));
}

// These need to be last in order for the `to_printable()` calls inside to
// pick up all the above implementations (plus any others via ADL).

Expand Down
26 changes: 10 additions & 16 deletions test/output/test_to_printable.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,6 @@ auto stringified(T &&thing) {
);
}

auto nil() {
std::ostringstream ss;
ss << static_cast<void*>(0);
return stringified(ss.str());
}

struct my_type {};
std::string to_printable(const my_type &) {
return "{my_type}";
Expand Down Expand Up @@ -83,12 +77,12 @@ suite<> test_to_printable("to_printable()", [](auto &_) {
expect(nullptr, stringified("nullptr"));

void *x = 0;
expect(x, nil());
expect(const_cast<const void*>(x), nil());
expect(x, stringified("nullptr"));
expect(const_cast<const void*>(x), stringified("nullptr"));

int *y = 0;
expect(y, nil());
expect(const_cast<const int*>(y), nil());
expect(y, stringified("nullptr"));
expect(const_cast<const int*>(y), stringified("nullptr"));

struct some_type {};
expect(some_type{}, stringified(none("true", "1")));
Expand Down Expand Up @@ -239,7 +233,7 @@ suite<> test_to_printable("to_printable()", [](auto &_) {
expect(static_cast<const char*>(cs), stringified("\"text\""));

char *ns = nullptr;
expect(ns, nil());
expect(ns, stringified("nullptr"));
});

_.test("signed char", []() {
Expand All @@ -257,7 +251,7 @@ suite<> test_to_printable("to_printable()", [](auto &_) {
expect(static_cast<const signed char*>(cs), stringified("\"text\""));

signed char *ns = nullptr;
expect(ns, nil());
expect(ns, stringified("nullptr"));
});

_.test("unsigned char", []() {
Expand All @@ -275,7 +269,7 @@ suite<> test_to_printable("to_printable()", [](auto &_) {
expect(static_cast<const unsigned char*>(cs), stringified("\"text\""));

unsigned char *ns = nullptr;
expect(ns, nil());
expect(ns, stringified("nullptr"));
});

_.test("wchar_t", []() {
Expand All @@ -299,7 +293,7 @@ suite<> test_to_printable("to_printable()", [](auto &_) {
expect(static_cast<const wchar_t*>(cs), stringified("\"text\""));

wchar_t *ns = nullptr;
expect(ns, nil());
expect(ns, stringified("nullptr"));
});

_.test("char16_t", []() {
Expand All @@ -323,7 +317,7 @@ suite<> test_to_printable("to_printable()", [](auto &_) {
expect(static_cast<const char16_t*>(cs), stringified("\"text\""));

char16_t *ns = nullptr;
expect(ns, nil());
expect(ns, stringified("nullptr"));
});

_.test("char32_t", []() {
Expand All @@ -347,7 +341,7 @@ suite<> test_to_printable("to_printable()", [](auto &_) {
expect(static_cast<const char32_t*>(cs), stringified("\"text\""));

char32_t *ns = nullptr;
expect(ns, nil());
expect(ns, stringified("nullptr"));
});
});
});

0 comments on commit 2da2fc0

Please sign in to comment.