diff --git a/include/mtl/string.hpp b/include/mtl/string.hpp index 1d3f96f..f627048 100644 --- a/include/mtl/string.hpp +++ b/include/mtl/string.hpp @@ -156,6 +156,99 @@ public: bool operator==(const string_view& rhs) const; bool operator!=(const string_view& rhs) const; + + /** + * \brief Convert the signed integer to a string + * + * The value in str is overwritten. + */ + template , bool> = true> + friend istring& to_string(T x, istring& str, bool hex = false) { + size_t num_char = 0; +#ifdef __ARM_ARCH_4T__ + if (hex) { + num_char = mtl_itostrx(x, str.data()); + } else { + num_char = mtl_itostr(x, str.data()); + } +#else + itoa(x, str.data(), hex ? 16 : 10); + num_char = strlen(str.data()); +#endif + str.m_size = num_char; + return str; + } + + /** + * \brief Convert the unsigned integer to a string + * + * The value in str is overwritten. + * + * The template must check that the integer is not a boolean because + * std::is_unsigned counts booleans as unsigned integers. + */ + template + && !std::is_same_v, bool> = true> + friend istring& to_string(T x, istring& str, bool hex = false) { + size_t num_char = 0; +#ifdef __ARM_ARCH_4T__ + if (hex) { + num_char = mtl_utostrx(x, str.data()); + } else { + num_char = mtl_utostr(x, str.data()); + } +#else + utoa(x, str.data(), hex ? 16 : 10); + num_char = strlen(str.data()); +#endif + str.m_size = num_char; + return str; + } + + /** + * \brief Convert the boolean to a string, using the provided buffer + * + * Writes the boolean as either "true" or "false". Depending on how + * this function is used, `x ? "true" : "false"` may be faster. + * Ex. mtl::string_stream does not use this function under the hood. + * + * The value in str is overwritten. + * + * This function needs to be templated otherwise non-boolean arguments + * could be implicitly converted to boolean. + */ + template , bool> = true> + friend istring& to_string(T x, istring& str) { + str = x ? "true" : "false"; + return str; + } + + /** + * \brief Convert the address value to a string, using the provided buffer + * + * Always writes the address in hexidecimal format. Does not pad the + * value to the address width. + * + * The value in str is overwritten. + * + * The template must check that the pointer is not a character pointer + * otherwise C strings will be converted to their address string, not + * the C string. + */ + template + && !std::is_same_v + && !std::is_same_v, bool> = true> + friend istring& to_string(T x, istring& str) { + size_t num_char = 0; +#ifdef __ARM_ARCH_4T__ + num_char = mtl_utostrx(reinterpret_cast(x), str.data()); +#else + utoa(x, str.data(), 16); + num_char = strlen(str.data()); +#endif + str.m_size = num_char; + return str; + } }; template @@ -183,4 +276,5 @@ public: using istring::operator=; }; + } // namespace ml