priority_queue重载小于运算符的问题

template <class T, class Container = vector<T>,
  class Compare = less<typename Container::value_type> > class priority_queue;

priority_queue的声明,可以看到底层默认是用vector实现的,并且第三个参数比较器默认是less

less的定义:

template<class T>
struct less:public binary_function<T,T,bool>{
    bool operator()(const T& x,const T& y) const {return x<y;}
}

注意这里有个注意点,less的重载函数调用运算符的参数是const T&,其实这很正常,但是因为x是const,所以假如我们在T这个类的成员函数里实现重载< 运算符的时候,就要把它定义成 const 成员函数,不然程序error,因为常量对象无法调用非const成员函数——因为this指针默认是指向非常量对象的常量指针 T * const this (也就是非const 成员函数的this参数类型), 而一个底层const不能初始化一个普通的对象, const成员函数的this参数类型是 const T * const this。

在这里,我还学到了当成员函数不改变数据成员的时候,一定要切记定义成const成员函数,虽然之前就学过,但好像一直没当回事。在定义函数参数的时候,好多时候都是写成const T&,所以假如不是const成员函数,就没法被调用。

 

tips2:

默认是less,也就是用<确定优先级,并且是越大的优先级越大,所以默认是大顶堆

(记住跟谁都是false 的优先度最高)

//小顶堆
priority_queue<int,vector<int>,greater<int> > small_heap;

//大顶堆
priority_queue<int> big_heap;

 tips3:

假如要定义自己的排序方法,我们要传给第三个模板参数是类,这里跟泛型算法不同,我之前想传lambda表达式,gg,因为lambda表达式实际上是一个未命名对象,而不是类,要想定义自己的排序方法有:
1) 类重载< 或者>运算符  (假如重载的是< 就用默认的less,假如重载的是>就用greater<T>),重载运算符可以是成员函数,但一定要是const成员函数,也可以是类T的(友元)全局函数,但是参数同样要是const T& 或者 传值 T 也ojbk

2)写一个函数类(重载了调用运算符的)

3)重头戏:

  priority_queue() : c() {}
  explicit priority_queue(const Compare& x) :  c(), comp(x) {}

priority_queue的构造函数有这样两种,所以除了上面两种方法,我们还能用函数指针或者lambda的方式来实现定义自己的排序方法,但是要注意< > 这里的第三个参数依然要是类,而不能是一个对象,所以要么使用decltype  (假如是函数指针的话,一定要 decltype(fun)*,最后的 * 别忘了加) 或者显式的用 function<返回类型 ( 参数 )  >

priority_queue<student, vector<student>, decltype(cmpfunc) *> que1(cmpfunc); // 注意一定要加上 *
priority_queue<student, vector<student>, function<bool(const student&, const student&)>> que1([](const student & a, const student & b) {return a.age < b.age; });

这里的组合方法就有很多了。

 

全部代码:
 

class student {
public:
	int age;
	string name;
	/**重载小于操作符,
	*可以成员,但一定要是const成员,也可以是非成员函数,但参数一定要是 const student& 或者 传值才可以
	*/

	 bool operator<(const student & b) const {   //必须要用const
		return this->age < b.age;
	}

	 friend bool operator<(const student& a, const student & b) {
		 return a.age < b.age;
	 }
	student(int _age, string _name) :age(_age), name(_name) {}
};

/**可调用的函数操作符的对象*/
struct mycmp {
	bool operator()(const student & a, const student & b) {
		return a.age < b.age;
	}
};

/**函数指针*/
bool cmpfunc(const student& a, const student& b) {
	return a.age < b.age;
}


int main() {

	/**默认使用student的oprator<来进行比较*/
	priority_queue<student> que1;

	
	/**使用重载函数操作符的类对象*/
	priority_queue<student, vector<student>, mycmp> que2;

	/*使用函数指针的形式*/
	priority_queue<student, vector<student>, decltype(cmpfunc) *> que3(cmpfunc); // 注意一定要加上 *

	/**使用lambda表达式*/
	auto cmp = [](const student & a, const student & b) {return a.age < b.age; };

	priority_queue<student, vector<student>, decltype(cmp)> que4(cmp);

	/**
	* 需要把lambda表达式作为优先队列参数进行初始化
	* 并且指定priority_queue的模板实参,decltype(cmp),
	* 可以认为是确定函数的类型
	* bool (const student & a,const student & b)
	**/

	//使用lambda表达式方法2
	priority_queue<student, vector<student>, function<bool(const student&, const student&)>> que5([](const student & a, const student & b) {return a.age < b.age; });

	//使用函数指针方法2

	//函数指针来初始化函数对象
	priority_queue<student, vector<student>, function<bool(const student&, const student&)>> que6(cmpfunc);

	system("pause");
}

 

  • 2
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值