为什么不能在std :: sort()比较函数中使用“return lhs.size()== rhs.size()”?

时间:2016-07-17 08:53:32

标签: c++

正如标题所说,我写了一个测试演示

bool comp(string lhs, string rhs) {
    return lhs.size() < rhs.size();
}

bool comp1(string lhs, string rhs) {
    return lhs.size() == rhs.size();
}

int main(int argc, const char *argv[]) {
    string str[] = {"dog", "is", "cat", "elephant", "fish", "cow"};
    std::sort(str, str + 6, comp1);
    output();
}

输出:cat dog is elephant fish cow

预期:...cat dog cow...

我想将这些相同大小的字符串放在一起,但它不起作用,有什么问题?

2 个答案:

答案 0 :(得分:3)

因为comp1(a,b)comp1(b,a)都可以返回true,这是不允许的。 std::sort声明:

  

comp - 比较函数对象(即满足Compare要求的对象),如果第一个参数小于(即在之前排序)第二个参数,则返回true。

按照Compare的链接,我们也会看到:

  

与以下属性建立strict weak ordering关系
  *对于所有a,comp(a,a)== false
  *如果comp(a,b)== true则comp(b,a)== false
  *如果comp(a,b)== true和comp(b,c)== true则comp(a,c)== true

您的第一个函数comp满足这些要求:没有两个对象可以返回true。如果comp(a,b)返回true,,则comp(b,a)会返回false;但是,在您的第二个函数comp1中并非如此。 comp1(a,b)可以true返回comp(b,a),因此sort永远不会完成,因此无法编译。

你说明了

  

我想将相同大小的字符串放在一起

但是只使用operator<将获得这些结果:任何相同大小的字符串将被组合在一起。

答案 1 :(得分:2)

==不会形成strict weak order。根据您的描述,以下内容应该是理想的:

bool comp(string const& lhs, string const& rhs) {
    return lhs.size() < rhs.size();
}

或者,如果您想要对相同长度的字符串进行词典排序:

bool comp(string const& lhs, string const& rhs) {
    return
        lhs.size() < rhs.size()
     || (lhs.size() == rhs.size() && lhs < rhs);
}

如需进一步阅读,这是我最喜欢的关于该主题的文章:Order I Say!