Skip to content
This repository has been archived by the owner on Apr 29, 2024. It is now read-only.

Commit

Permalink
Fix comparing strings with raw string literals and count parameter fo…
Browse files Browse the repository at this point in the history
…r partial comparisons
  • Loading branch information
Hammie committed Dec 30, 2021
1 parent d373499 commit 2ed0c42
Show file tree
Hide file tree
Showing 2 changed files with 65 additions and 7 deletions.
58 changes: 51 additions & 7 deletions src/libs/util/include/storm/string_compare.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -34,28 +34,72 @@ struct is_iless_eq

} // namespace detail

template <typename Range1T, typename Range2T = Range1T>
bool iEquals(const Range1T &first, const Range2T &second, const size_t count)
{
detail::is_iequal comp;

const auto &first_normalized = std::is_pointer<Range1T>::value ? std::string_view(first) : first;
const auto &second_normalized = std::is_pointer<Range1T>::value ? std::string_view(second) : second;

const auto first_begin = std::begin(first_normalized);
const auto second_begin = std::begin(second_normalized);

const auto first_end = std::end(first_normalized);
const auto second_end = std::end(second_normalized);

const auto first_length = std::distance(first_begin, first_end) - 1;
const auto second_length = std::distance(first_begin, first_end) - 1;
if (first_length < count || second_length < count)
{
if (first_length != second_length)
{
return false;
}
else
{
return std::equal(first_begin, first_begin + first_length, second_begin, second_begin + second_length,
comp);
}
}
else
{
return std::equal(first_begin, first_end, second_begin, second_end, comp);
}
}

template <typename Range1T, typename Range2T = Range1T> bool iEquals(const Range1T &first, const Range2T &second)
{
detail::is_iequal comp;

const auto first_begin = std::begin(first);
const auto second_begin = std::begin(second);
const auto &first_normalized = std::is_pointer<Range1T>::value ? std::string_view(first) : first;
const auto &second_normalized = std::is_pointer<Range1T>::value ? std::string_view(second) : second;

const auto first_begin = std::begin(first_normalized);
const auto second_begin = std::begin(second_normalized);

const auto first_end = std::end(first);
const auto second_end = std::end(second);
const auto first_end = std::end(first_normalized);
const auto second_end = std::end(second_normalized);

return std::equal(first_begin, first_end, second_begin, second_end, comp);
}

template <typename Range1T, typename Range2T = Range1T> bool iLess(const Range1T &first, const Range2T &second)
{
return std::lexicographical_compare(std::begin(first), std::end(first), std::begin(second), std::end(second),
detail::is_iless{});
const auto &first_normalized = std::is_pointer<Range1T>::value ? std::string_view(first) : first;
const auto &second_normalized = std::is_pointer<Range1T>::value ? std::string_view(second) : second;

return std::lexicographical_compare(std::begin(first_normalized), std::end(first_normalized),
std::begin(second_normalized), std::end(second_normalized), detail::is_iless{});
}

template <typename Range1T, typename Range2T = Range1T> bool iLessOrEqual(const Range1T &first, const Range2T &second)
{
return std::lexicographical_compare(std::begin(first), std::end(first), std::begin(second), std::end(second),
const auto &first_normalized = std::is_pointer<Range1T>::value ? std::string_view(first) : first;
const auto &second_normalized = std::is_pointer<Range1T>::value ? std::string_view(second) : second;

return std::lexicographical_compare(std::begin(first_normalized), std::end(first_normalized),
std::begin(second_normalized), std::end(second_normalized),
detail::is_iless_eq{});
}

Expand Down
14 changes: 14 additions & 0 deletions src/libs/util/testsuite/string_compare.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,20 @@ TEST_CASE("Case-insensitive string comparison", "[utils]")
{
CHECK_FALSE(iEquals(str_lowercase, str_long));
}

SECTION("Compare with raw char string literal")
{
CHECK(iEquals(str_lowercase, "myString"));

const char string_array[] = "myString";
CHECK(iEquals(string_array, str_lowercase));

}

SECTION("Compare only count number of character at most")
{
CHECK(iEquals(str_lowercase, str_long, 8));
}
}

SECTION("iLess")
Expand Down

0 comments on commit 2ed0c42

Please sign in to comment.