diff --git a/include/stdex/string.hpp b/include/stdex/string.hpp index 5440db6a8..b41701faf 100644 --- a/include/stdex/string.hpp +++ b/include/stdex/string.hpp @@ -1066,6 +1066,103 @@ namespace stdex reinterpret_cast(str2), N2); } + /// + /// Binary compare two strings + /// + /// \param[in] str1 String 1 + /// \param[in] count1 String 1 code unit count limit + /// \param[in] str2 String 2 + /// \param[in] count2 String 2 code unit count limit + /// + /// \return Negative if str1str2; zero if str1==str2 + /// + inline int strncmp( + _In_reads_or_z_opt_(count1) const utf16_t* str1, _In_ size_t count1, + _In_reads_or_z_opt_(count2) const utf16_t* str2, _In_ size_t count2) + { + stdex_assert(str1 || !count1); + stdex_assert(str2 || !count2); + for (size_t i = 0, j = 0; ;) { + if (i >= count1 && j >= count2) return 0; + if (i >= count1 && j < count2) return -1; + if (i < count1 && j >= count2) return +1; + + utf32_t a; + if (i + 1 >= count1 || !is_surrogate_pair(&str1[i])) { + a = static_cast(str1[i]); + i++; + } + else { + a = surrogate_pair_to_ucs4(&str1[i]); + i += 2; + } + utf32_t b; + if (j + 1 >= count2 || !is_surrogate_pair(&str2[j])) { + b = static_cast(str2[j]); + j++; + } + else { + b = surrogate_pair_to_ucs4(&str2[j]); + j += 2; + } + if (a < b) return -1; + if (a > b) return +1; + } + } + + /// + /// Binary compare two strings + /// + /// \param[in] str1 String 1 + /// \param[in] count1 String 1 code unit count limit + /// \param[in] str2 String 2 + /// \param[in] count2 String 2 code unit count limit + /// + /// \return Negative if str1str2; zero if str1==str2 + /// + inline int strncmp( + _In_reads_or_z_opt_(count1) const char16_t* str1, _In_ size_t count1, + _In_reads_or_z_opt_(count2) const char16_t* str2, _In_ size_t count2) + { + return strncmp( + reinterpret_cast(str1), count1, + reinterpret_cast(str2), count2); + } + + /// + /// Binary compare two strings + /// + /// \param[in] str1 String 1 + /// \param[in] str2 String 2 + /// + /// \return Negative if str1str2; zero if str1==str2 + /// + template + int strncmp( + _In_ const utf16_t(&str1)[N1], + _In_ const utf16_t(&str2)[N2]) + { + return strncmp(str1, N1, str2, N2); + } + + /// + /// Binary compare two strings + /// + /// \param[in] str1 String 1 + /// \param[in] str2 String 2 + /// + /// \return Negative if str1str2; zero if str1==str2 + /// + template + int strncmp( + _In_ const char16_t(&str1)[N1], + _In_ const char16_t(&str2)[N2]) + { + return strncmp( + reinterpret_cast(str1), N1, + reinterpret_cast(str2), N2); + } + /// /// Binary compare two strings in reverse direction ///