为什么函数比较器不像排序那样在优先级队列中工作?

时间:2016-01-18 09:11:11

标签: c++ sorting stl compare priority-queue

我们有question,讨论如何在C ++中使用priority_queue中的比较器。他将重载的operator class(或struct)作为第三个参数,它可以正常工作。但bool功能并不起作用。为什么?但它在sort的{​​{1}}中工作正常。当我查看文档(priority_queue&amp;&amp; algo/sort)时,他们都将<algorithm>作为可选的第三个参数。

class Compare

错误:

#include <iostream>
#include <cstdio>
#include <queue>
#include <algorithm>
#include <vector>

using namespace std;

bool cmp (const int &a,const int &b){ return a > b; }

struct cmp2
{
    bool operator() (const int &p1,const int &p2)
    {
        return p1 > p2;
    }
};

int main ()
{
//  freopen("test.txt","r",stdin);
    int a[10];
    vector<int> b(10);
    sort( a , a + 10, cmp );    // working cool
    sort( b.begin() , b.end() , cmp);   // working great
    priority_queue<int, vector<int> , cmp2 > x;    // as usual, working....
    priority_queue<int, vector<int> , cmp > y;   // not working why ?

    return 0;
}

那么,差异为何呢?

3 个答案:

答案 0 :(得分:4)

您也可以使用std::priority_queue的功能。您正在做的事情的不同之处在于您将函数作为函数参数传递给std::sort,但您尝试将该函数定义为队列的模板参数。这显然不起作用,因为第三个参数是错误解释的类型参数。此外,你甚至不能有指针或参考模板参数。

如果查看reference,您会发现队列中有一个用于传递比较对象的构造函数。 那是你必须传递函数的地方。

std::sort存在差异。 Sort是一个函数,您可以让编译器deduce使用它的模板参数,这样您就不必明确指定它们。队列是一个类模板,并且不能推导出类模板的模板参数(至少不在此上下文中)。

模板参数默认为std::less<typename Container::value_type>,但您不想使用它。因此,您必须明确指定比较对象的类型。您可以在现在尝试传递对象的位置指定它。你可能会问,如何获取函数指针/引用的类型。您可以这样做:decltype(&cmp)。如果您的过时编译器还不支持decltype,那么您需要指定不带它的类型:bool (&)(const int&, const int&)

以下是如何创建使用您的函数的队列的示例。

std::priority_queue<int, std::vector<int>, decltype(&cmp)> x(cmp);

答案 1 :(得分:2)

如错误消息所示,函数不能用作模板参数。 priority_queue将复制比较类型的对象。例如,这可能是std::less<int>,其中该类型的对象是std::less<int>(),并且它被称为std::less<int>()(x, y)。在C ++ 11中,您可以使用decltype,但在C ++ 03中使用&#34;规范&#34;方法是创建一个&#34;仿函数&#34; (专用于作为函数对象的整个类型。)这是创建lambdas的原因之一。

答案 2 :(得分:1)

答案是编译器错误。 优先级队列的第三个模板参数是比较器类型(如结构或类),而不是函数。