【问题标题】:std::sort Doesn't work for User-Defined Object with oveloaded < operatorstd :: sort不适用于具有Oveloaded <Operator的用户定义对象
【发布时间】:2017-08-28 17:09:05
【问题描述】:

我正在编写一个类来测试不同排序算法(对于大学课程)的效率,而我应该测试的算法是 STL 排序。为了衡量效率,我们定义了一个 Integer 类,它保存整数值,并且还允许我们在每次比较或分配全局变量时递增它。然后我有一个驱动程序类,它测试对多个整数向量的 std::sort 调用。我在我的 Integer 类中重载了 '

整数.cpp

#include "Integer.h"

int Integer_count;

//Default Constructor
Integer::Integer() {
    val = 0;
}

//Specified Constructor
Integer::Integer(int x) {
    val = x;
}

//Copy-Constructor
Integer::Integer(const Integer &cp) {
    Integer_count++;
    val = cp.val;
}

//Return the Integer's value
int Integer::value() {
    return val;
}

//Less-than (<) operator overload
bool Integer::operator < (const Integer& obj) const {
    Integer_count++;
    return (val < obj.val);
}

//Assignment (=) operator overload
void Integer::operator = (const Integer& obj) {
    Integer_count++;
    val=obj.val;
}

driver.cpp

#include <iostream>
#include <cstdlib>
#include <vector>
#include "Integer.h"
#include "Sorter.cpp"    
srand (time(NULL)); //Seed the random number generator

    std::vector<Integer> one;
    std::vector<Integer> two;
    std::vector<Integer> three;
    std::vector<Integer> four;
    std::vector<Integer> five;


    for(int i=0; i<10000; i++){
        one[i] = Integer(i);
        two[i] = Integer(10000-i);
        three[i] = Integer(rand() % (10000+1));
        four[i] = Integer(rand() % (10000+1));
        five[i] = Integer(rand() % (10000+1));
    }


    //Sort function called from the STL
    //Sorted Array
    std::sort(one.begin(), one.end());
    std::cout << "STL for Sorted Array: " << Integer_count << std::endl;

基本上,我认为 std::sort 函数没有使用我的 Integer 类中的重载运算符,这会弄乱堆栈。我不确定这是不是错误,但似乎无法解决。

【问题讨论】:

  • 您没有为 std::vectors 分配任何空间。 one[i] 不创建新元素。使用one.push_back(Integer(i));
  • vector[] 不插入新元素 - 使用 push_back 代替
  • 要保留向量空间,例如写std::vector&lt;Integer&gt; one(10000)。替代方案:one.reserve(10000) 并在循环中使用one.push_back(Integer(i)) 而不是赋值。

标签: c++ algorithm sorting c++11 stl


【解决方案1】:

您的 vector[i] 值未分配。因此,访问超出范围的向量值(例如one[999999])会导致未定义的行为。

使用push_back() 为您的std:::vector 分配值并将其分配给您的向量:

for(int i=0; i<10000; i++){
    one.push_back(Integer(i));
    two.push_back(Integer(10000-i));
    three.push_back(Integer(rand() % (10000+1)));
    four.push_back(Integer(rand() % (10000+1)));
    five.push_back(Integer(rand() % (10000+1)));
}

这将解决分段错误。 至于排序,一旦你有了值。

std::sort(one.begin(), one.end()) sorts by default using operator&lt; 就这样吧。

【讨论】:

  • 错字,快速解答。谢谢@4386427
【解决方案2】:

您没有在向量中推送/附加元素。如果不分配空间或向后推,则不能以这种方式在向量中添加元素(我的 clang 编译器会由于分配错误/数组越界而产生运行时错误)。请改用push_back

快速测试-

std::vector<Integer> arr{Integer(1), Integer(4), Integer(3)};
sort(arr.begin(), arr.end());

// now print Integer_count

【讨论】:

    【解决方案3】:

    std::vector::operator[] 从不向容器中插入新元素并且不执行边界检查 (vector/operator_at)。如果您访问超出范围的元素会导致未定义的行为,这就是您的情况。

    您必须使用std::vector::emplace_backstd::vector::push_back,其他选项是使用构造函数explicit vector&lt;T&gt;(size_type count);,该构造函数使用count 默认插入的T 实例来构造容器:

    第一个选项:

    std::vector<Integer> one;
    one.reserve(10000);
    std::vector<Integer> two;
    two.reserve(10000);
    std::vector<Integer> three;
    three.reserve(10000);
    std::vector<Integer> four;
    four.reserve(10000);
    std::vector<Integer> five;
    five.reserve(10000);
    
    for (int i = 0; i < 10000; ++i) {
        one.emplace_back(i);
        two.emplace_back(10000 - i);
        three.emplace_back(rand() % (10000+1));
        four.emplace_back(rand() % (10000+1));
        five.emplace_back(rand() % (10000+1));
    }
    

    第二个选项:

    std::vector<Integer> one(10000);
    std::vector<Integer> two(10000);
    std::vector<Integer> three(10000);
    std::vector<Integer> four(10000);
    std::vector<Integer> five(10000);
    
    for (int i = 0; i < 10000; ++i) {
        one[i] = Integer(i);
        two[i] = Integer(10000-i);
        three[i] = Integer(rand() % (10000+1));
        four[i] = Integer(rand() % (10000+1));
        five[i] = Integer(rand() % (10000+1));
    }
    

    std::sort(one.begin(), one.end()) 必须工作。

    【讨论】:

    • 非常感谢 - 试图快速破解它并忘记了最简单的语法。我的坏:)
    猜你喜欢
    • 1970-01-01
    • 2019-10-31
    • 1970-01-01
    • 1970-01-01
    • 2021-10-09
    • 1970-01-01
    • 2021-05-10
    • 2015-06-13
    • 2013-04-17
    相关资源
    最近更新 更多