我尝试理解在STL类模板中使用的运算符重载,例如:map或pair。
让我向您介绍我的代码:
#include <iostream>
#include <iomanip> // left, setw
#include <string>
#include <map>
#include <utility> // pair
#include <algorithm> // count if
using namespace std;
typedef pair <string, int> Emp;
typedef map <string, Emp> MAP;
class Zakr{
int min, max;
public:
Zakr(int min, int max): min(min), max(max){}
bool operator()(const pair<const string, Emp> &p) const{
int wage = p.second.second;
return (min < wage) && (wage < max);
}
};
void print (const MAP& m) {
MAP::const_iterator it, fin = m.end();
for(it = m.begin(); it != fin; it++)
cout << "Key: " << left << setw(7) << it -> first
<< "Name: " << setw(10) << it->second.first
<< "Wage: " << it->second.second << endl;
}
int main(void){
MAP emp;
MAP object;
emp["John"] = Emp("John K.", 1900);
emp["Tania"] = Emp("Tania L.", 1900);
emp["Jeremy"] = Emp("Jeremy C", 2100);
emp["Susie"] = Emp("Susie W.", 3100);
emp["Toto"] = Emp("Toto T.", 9900);
emp["Adrian"] = Emp("Adrian N.", 1600);
emp["Germy"] = Emp("Germy P.", 2600);
print(emp);
int mn = 0, mx = 2000;
int how_much = count_if(emp.begin(), emp.end(), Zakr(mn, mx));
cout << how_much << " earn from"
<< mn << " to " << mx << endl;
}
我很难理解某些内容,特别是一些内容,即:
class Zakr{
int min, max;
public:
Zakr(int min, int max): min(min), max(max){}
bool operator()(const pair<const string, Emp> &p) const{
int wage = p.second.second;
return (min < wage) && (wage < max);
}
};
所以我构建了一个名为Zakr的类,这样我就可以使用它来确定count_if语句中的函子。
我是对的吗?
我初始化私有字段,min和max以在构造函数中使用它们,而不是因为已经重载的运算符可以根据它们自己的值返回布尔值。 最困难的部分是了解bool运算符重载。
bool operator()(const pair<const string, Emp> &p) const{
int wage = p.second.second;
为什么我需要1 *制作一对无用的字符串值和EMP?
由于我感兴趣的所有人都存储在EMP中,即:将在重载中使用的int值存储在Emp中。
为什么我不能像以下那样访问存储在Emp中的int:
bool operator(Emp &p)
{
int wage = p.second;
return (min < wage) && (wage < max);
}
为什么我需要制作另外一对:( const pair&amp; p),如果我感兴趣的是存储在名为Emp的对中的值。
为什么我需要使用上面命名对的无用的第一个元素来创建另一对:string。 我不打算使用它,为什么需要编译代码呢?
我尽力解释我的怀疑,尽可能清楚。 希望有人会理解这个相当长的帖子。
干杯!
答案 0 :(得分:2)
这是因为std::map
以上的迭代器会为每个元素返回std::pair
。该对中的第一项是地图键,第二项是地图值。请参阅documentation for std::map
中的value_type
。
This question对于如何仅在地图的值上获取迭代器有一些答案。
答案 1 :(得分:0)
<强> 1。 Zakr类:
实际上,它通常与count_if()
一起使用。如果您查看该链接,您会看到count_if(first, last, pred)
等同于:
int ret = 0;
while (first!=last) {
if (pred(*first)) ++ret; // works as soon as object pred has operator() defined.
++first;
}
return ret;
<强> 2。为什么在operator()中需要一对:
map适用于对,每个对都由唯一键和相应的值组成。
这部分是隐藏的。例如,当您将地图用作表达为emp["John"]
的关联数组时,地图将找到具有唯一键“John”的对,并返回对相应值的引用。
但是,只要遍历地图,迭代器就会解决这些对。为什么?因为如果它只是遍历值,你会获得价值,但你永远不知道它对应哪个唯一键。
结果:count_if()
遍历映射,因此使用迭代器调用谓词来寻址一对。
第3。为什么要做一个无用的配对:
首先,计数功能不会创建虚拟对。它使用对现有对的引用(从性能的角度来看,它不会超过传递指针的成本!)
而且,地图是为了解决一般问题。您有一天可能有兴趣不仅计算工资,而且还计算相关关键字(例如:名称以'A'开头的员工的范围内的所有工资都不计算)。