我有string s="java"
和map<string,int>M
。 M
包含
(Cpp,1), (jAvA,2), (Cobol,3)
。我必须检查string s
是否与地图中的任何键匹配(不区分大小写)。 Is there any better way than iterating through entire map and check for each record
?在此示例中,字符串s应与map中的第二个记录匹配,因为它不区分大小写匹配。在以下示例中,我们将compareInterval()
与sort()
一起使用。有没有办法可以使用stricmp()的任何函数并使用map M和string s并有效地执行不区分大小写的匹配?
// A C++ program to demonstrate STL sort() using
// our own comparator
#include<bits/stdc++.h>
using namespace std;
// An interval has start time and end time
struct Interval
{
int start, end;
};
// Compares two intervals according to staring times.
bool compareInterval(Interval i1, Interval i2)
{
return (i1.start < i2.start);
}
int main()
{
Interval arr[] = { {6,8}, {1,9}, {2,4}, {4,7} };
int n = sizeof(arr)/sizeof(arr[0]);
// sort the intervals in increasing order of
// start time
sort(arr, arr+n, compareInterval);
cout << "Intervals sorted by start time : \n";
for (int i=0; i<n; i++)
cout << "[" << arr[i].start << "," << arr[i].end
<< "] ";
return 0;
}
答案 0 :(得分:1)
您可以为地图使用不区分大小写的比较器:
struct CaseInsensitiveLess
{
bool operator()(std::string lhs, std::string rhs)
{
std::transform(lhs.begin(), lhs.end(), lhs.begin(),
[](char c) { return std::tolower(c); });
std::transform(rhs.begin(), rhs.end(), rhs.begin(),
[](char c) { return std::tolower(c); });
return lhs < rhs;
}
};
int main()
{
std::map<std::string, int, CaseInsensitiveLess> foo = {
{"Cpp", 1}, {"jAvA", 2}, {"Cobol", 3}
};
std::cout << foo["java"] << '\n';
}
这会在比较字符串时将字符串转换为小写字母,因此在插入时,"java"
,"Java"
,"jAvA"
,"JAVA"
等都会被视为相同的字符串地图或查找其中的值。
答案 1 :(得分:0)
有没有比迭代整个地图并检查每条记录更好的方法?
需要完成此操作,因为您无法使用std::map::find
,这将更有效地工作。您可以使用std::find_if
来减少一些样板代码,但仍然意味着您正在迭代map
的每个项目。
但更重要的是,如果您要使用不区分大小写的比较来搜索键,最好还使用不区分大小写的比较函数/仿函数来创建映射。否则,map
中可能有多个元素,例如:
(jAvA, 2)
(java, 20)
(JAVA, 30)
然后搜索功能不一定能为您提供您想要的项目。