#include <iostream>
#include <thread>
#include <regex>
#include <string>
#include <algorithm>
#include <absl/strings/match.h>
#include <atlstr.h>
struct NumberStringCompare
{
bool operator()(const std::string& a, const std::string& b)
{
auto split_str = [](const std::string& complex, std::string& prefix, std::string& suffix, bool is_num) -> void {
const static std::regex r_get_number(R"([\D])");
const static std::regex r_get_neg_number(R"([\d])");
const std::regex& reg = is_num ? r_get_number : r_get_neg_number;
std::cmatch m;
if (std::regex_search(complex.c_str(), m, reg))
{
prefix = m.prefix();
suffix = m.str() + m.suffix().str();
}
else
{
prefix = complex;
suffix = "";
}
};
std::string pa, pb, sa(a), sb(b);
while (!sa.empty()||!sb.empty())
{
split_str(sa, pa, sa, true);
split_str(sb, pb, sb, true);
if (pa != pb)
{
if (pa.empty()) return sa.empty();
if (pb.empty()) return !sb.empty();
if (pa.size() != pb.size())
{
std::string& p = pa.size() < pb.size() ? pa : pb;
for (decltype(p.size()) i = 0; i < std::abs((long long)(pa.size() - pb.size())); ++i)
p = "0" + p;
}
if (pa != pb)
return pa < pb;
}
split_str(sa, pa, sa, false);
split_str(sb, pb, sb, false);
CStringA str_pa(pa.c_str());
auto ret = str_pa.CompareNoCase(pb.c_str());
if (ret != 0)
return ret < 0;
}
return true;
}
};
int main()
{
std::vector<std::string> strs({ "abc","ABCD","3","2", "AB","abcde", "10", "01", "abc10", "abc2" });
std::sort(strs.begin(), strs.end(), NumberStringCompare());
std::sort(strs.rbegin(), strs.rend(), NumberStringCompare());
OutputDebugStringA("");
}