方法一,mismatch()
/**
* @brief 忽略大小写比较字符.
* @param c1 字符 c1.
* @param c2 字符 c2.
* @return int 若 c1 < c2, 则返回 -1; 若 c1 == c2, 则返回 0; 若 c1 > c2, 则返回 1.
*/
int ciCharCompare(char c1, char c2)
{
// tolower() 的参数和返回值的类型是 int, 除非这个 int 是 EOF,
// 否则它的值必须能表现为一个 unsigned char.
// 在 C 和 C++ 中, char 可能或不可能是有符号的, 当 char 有符号时,
// 唯一确认它的值可以表现为 unsigned char 的方式就是在调用 tolower() 之前
// 转换一下.
int lc1 = tolower(static_cast<unsigned char>(c1));
int lc2 = tolower(static_cast<unsigned char>(c2));
if (lc1 < lc2)
{
return -1;
}
if (lc1 > lc2)
{
return 1;
}
return 0;
}
int ciStringCompareImpl(const string &s1, const string &s2)
{
// PSCI = "a pair of string::const_iterator".
typedef pair<string::const_iterator, string::const_iterator> PSCI;
// mismatch() 算法返回一对迭代器, 表示了区间中第一个对应的字符不相同的位置.
PSCI p = mismatch(s1.begin(), s1.end(),
s2.begin(),
not2(ptr_fun(ciCharCompare)));
// 如果为真.
if (p.first == s1.end())
{
// s1 等于 s2.
if (p.second == s2.end())
{
return 0;
}
// 或者 s1 比 s2 短.
else
{
return -1;
}
}
// 两个字符串的关系和不匹配的字符一样.
return ciCharCompare(*p.first, *p.second);
}
int ciStringCompare(const string &s1, const string &s2)
{
if (s1.size() <= s2.size())
{
return ciStringComparelmpl(s1, s2);
}
else
{
return -ciStringComparelmpl(s2, s1);
}
}
方法二,lexicographical_compare()
将字符串比较工作交给 STL 中名字第二长的算法——lexicographical_compare()
,为其提供一个判断式接口比较函数 ciCharLess()
。
lexicographical_campare()
是 strcmp()
的泛型版本,其对任何类型的值的区间都起作用,可以传入一个决定两个值是否满足一个用户定义标准的二元判断式。
bool ciCharLess(char c1, char c2)
{
return tolower(static_cast<unsigned char>(c1)) <
tolower(static_cast<unsigned char>(c2));
}
bool ciStringCompare(const string &s1, const string &s2)
{
return lexicographical_compare(s1.begin(), s1.end(),
s2.begin(), s2.end(),
ciCharLess);
}
方法三,strcmp()
牺牲移植性,不关心国际化,取而代之,将两个字符串都转换为 const char*
指针,然后对指针使用 strcmp()
。
int ciStringCompare(const string &s1, const string &s2)
{
return strcmp(s1.c_str(), s2.c_str());
}