自定义排序会以意外的方式工作

问题描述 投票:1回答:1

我在以下自定义比较中获得了我的矢量元素排序所带来的意外结果。

int dateCompare(string d1,string d2)
{
    int rc;
    const char *d3 = d1.c_str();
    const char *d4 = d2.c_str();

    // compare years
    rc = strncmp(d3 + 6, d4 + 6, 4);
    if (rc != 0)
        return rc;

    // compare months
    rc = strncmp(d3 + 3, d4 + 3, 2);
    if (rc != 0)
        return rc;

    // compare days
    return strncmp(d3, d4, 2);
}


 vec.push_back("01/10/2015"); 
 vec.push_back("02/11/2015"); 
 vec.push_back("03/09/2015"); 
 sort(vec.begin(), vec.end(), dateCompare);

Input:
01/10/2015
02/11/2015
03/09/2015

Output:
03/09/2015
02/11/2015
01/10/2015

我知道还有其他更好的方法可以比较日期并更改元素本身的结构等。但不仅如此,我还想弄清楚为什么std::sort函数的工作方式没有差异,即为什么交换,无论比较器返回true还是false

[dateCompare()被这3个元素调用了两次。

First time =>被调用,并且在dateCompare("02/11/2015","01/10/2015")的求值期间,返回true,因此存在交换。因此,VEC从

更改为
strcmp(11,10)

第二时间->调用{"01/10/2015","02/11/2015","03/09/2015"} to {"02/11/2015","01/10/2015","03/09/2015"} ,并且在评估dateCompare("03/09/2015","02/11/2015")期间,返回false 并且不期望进行交换,但仍然交换了。所以vec从

更改
strcmp(09,11)

所以我更改了输入({"02/11/2015","01/10/2015","03/09/2015"} to {"03/09/2015","01/10/2015","02/11/2015"} 更改为03/09/2015),以便第二个比较返回true(而不是false),但它仍然会交换结果:

03/12/2015

无论返回值是01/10/2015 02/11/2015 03/12/2015 03/12/2015 02/11/2015 01/10/2015 还是true,它看起来都交换了

c++ algorithm sorting data-structures stl
1个回答
4
投票

false期望比较器返回一个布尔值-如果第一个参数应按排序顺序位于第二个参数之前,则为true,否则为false。像您一样,返回-1、0或1(小于,等于,大于)的比较器不适合std::sort;它违反了严格的弱排序要求。您的程序表现出未定义的行为。

© www.soinside.com 2019 - 2024. All rights reserved.