在学习C++的map的时候,写了一段代码

 

 
      
  1. #include <iostream> 
  2. #include <map> 
  3. using namespace std; 
  4.  
  5. class A 
  6.     public
  7.     A(){cout<<"A created"<<endl;} 
  8.     A(const A& a){cout<<"A created by another a"<<endl;} 
  9.     ~A(){cout<<"A destoried"<<endl;} 
  10.     friend ostream & operator << (ostream& os,const A& a) 
  11.     { 
  12.         os<<"print a"<<endl; 
  13.         return os; 
  14.     } 
  15. }; 
  16. int main(int argc, const char *argv[]) 
  17.  
  18.     A a1; 
  19.     A a2(a1); 
  20.     map<A,A> maa; 
  21.     //make_pair(a1,a2); 
  22.     maa.insert(make_pair(a1,a2)); 
  23.     return 0; 
这段代码在编译时出错了“/usr/include/c++/4.6/bits/stl_function.h:236:22: 错误: ‘operator<’在‘__x < __y’中没有匹配”,然而奇怪的是, 如果我把maa.insert(make_pair(a1,a2));改为make_pair(a1,a2);后就能顺利编译通过。看这个样子是在调用map的insert方法时编译出错的,但是为什么呢?

在网上疯狂搜索了一阵之后,发现一篇博文(http://blog.csdn.net/xie376450483/article/details/6329408)回答了出错的原因.这篇博文中提到两点:

1. "map内部存储机制实际是以红黑树为基础,红黑树在插入节点时,必须依照大小比对之后在一个合适的位置上执行插入动作。所以作为关键字,起码必须有“<”这个比较操作符。"

2. 由于STL中对less仿函数的定义为

 
  
  1. template <class _Tp> 
  2. struct less : public binary_function<_Tp,_Tp,bool
  3.  
  4.       bool operator()(const _Tp& __x, const _Tp& __y) const { return __x < __y; } 
  5. }; 

less调用这个比较符时,它都是以const方式传入,不可能再以非const方式调用.故不能使用定义成员函数bool operator < (const struct st &rs)  而必须以友联函数[friend bool operator < (const A& a,const A& b)]代替函数内部定义的比较操作符.

 在给类A加了一个operator<方法

 
  
  1. friend bool operator < (const A& a,const A& b) 
  2.     return true

后,再次编译就通过了.

其实从STL中map的定义也能看出端倪来,map的定义如下

 

 
  
  1. template < 
  2.    class Key, 
  3.    class Type, 
  4.    class Traits = less<Key>, 
  5.       class Allocator=allocator<pair <const Key, Type> > 
  6. class map 

要有比较谓词,而且默认用“<”