为什么这个std :: find能比较这些对象

时间:2017-09-27 04:07:11

标签: c++ c++11 std

通常当我做一个std :: find我会把一个谓词作为第三个参数,但这次我认为我做的不同,我不明白它为什么没有#&## 39;工作。

#include <iostream>
#include <vector>
#include <algorithm>

struct RenderJob
{
    RenderJob() {};
    int renderJob_ID;
    bool operator==(RenderJob& rhs) { return rhs.renderJob_ID == this->renderJob_ID; }
};

int main()
{
    RenderJob foo;
    RenderJob foo2;
    foo == foo2; // Works

    std::vector<RenderJob> renderJobs;

    std::find(renderJobs.begin(), renderJobs.end(), foo); // Doesn't work
}
  

二进制&#34; ==&#34;找不到哪个操作符需要左手操作数   输入RenderJob(或没有可接受的转换)

编辑::谢谢你的答案。以下是一些失败原因的例子

    RenderJob foo;
    RenderJob foo2;
    foo == foo2; // Works

    std::vector<RenderJob> renderJobs;

    std::vector<RenderJob>::const_iterator constit = renderJobs.begin();

    *constit == foo2;  // Doesn't work

更简单的说明:

 const RenderJob* pToRenderJob;

*pToRenderJob == foo2;  // This fails because the pointed to 
                        // object is const, and cannot call the 
                        // operator== function because the actual function
                        // definition is not const. 

如果是相反的方式:

foo2 == *pToRenderJob; // This would fail because the 
                        // operator==(RenderJob&) the actual argument 
                        // is not const. Very subtle rules

3 个答案:

答案 0 :(得分:14)

您离开了const个限定符。

bool operator==(const RenderJob& rhs) const { ... }

答案 1 :(得分:5)

在我看来,这是一个常量问题。尝试这样的事情:

bool operator==(RenderJob const &rhs) const { 
    return rhs.renderJob_ID == this->renderJob_ID; 
}

进行比较本身是有效的,因为你只是传递非临时的普通对象,也不是const限定的。对于std::find,比较函数将(至少通常)接收对集合中对象的引用(通常是const限定的),因此它需要能够接收const限定引用。

答案 2 :(得分:3)

  

但这仍然没有意义,在上面的示例中,右侧是foo2,这不是常量,应该转到非const operator== 。除非有一般规则const和非const无法比较。

语言中没有规则无法比较const和非const个对象。您必须确保使用正确的const限定符来比较它们。

该行

*pToRenderJob == foo2;

相当于

pToRenderJob->operator==(foo2);

这不起作用,因为pToRenderJob不能用于调用非const成员函数。 foo2不是问题所在。

如果您使用

foo2 == *pToRenderJob

等同于

foo2.operator==(*pToRenderJob)

这也是一个问题,因为函数的参数是const对象,而函数需要非const引用。再一次,foo2不是问题。

使函数成为const成员函数并使参数成为const引用,可确保const和非const对象的所有组合都位于运算符可以毫无问题地使用。