c ++中多线程快速排序期间的分段错误

时间:2017-01-12 09:37:03

标签: c++ multithreading quicksort

#include <iostream>
#include <algorithm>
#include <future>
#include <iterator>

using namespace std;

void qsort(int *beg, int *end)
{

    if (end - beg <= 1)
        return;

    int lhs = *beg;
    int *mid = partition(beg + 1, end, 
        [&](int arg)
        {
            return arg < lhs;
        }
    );

    swap(*beg, *(mid - 1));

    qsort(beg, mid);
    qsort(mid, end);
}

std::future<void> qsortMulti(int *beg, int *end) // SEG FAULT
{

    if (end - beg <= 1)
        return future<void>();
    int lhs = *beg;
    int *mid = partition(beg + 1, end, 
        [&](int arg)
        {
            return arg < lhs;
        }
    );

    swap(*beg, *(mid - 1));
    //spawn new thread for one side of the recursion
    auto future = async(launch::async, qsortMulti, beg, mid);
    //other side of the recursion is done in the current thread
    qsortMulti(mid, end);
    future.wait();
    inplace_merge(beg, mid, end);
}

void printArray(int *arr, size_t sz)
{
    for (size_t i = 0; i != sz; i++)
        cout << arr[i] << ' ';
    cout << endl;
}

int main()
{
    int ia[] = {5,3,6,8,4,6,2,5,2,9,7,8,4,2,6,8};
    int ia2[] = {5,3,6,8,4,6,2,5,2,9,7,8,4,2,6,8};
    size_t iaSize = 16;
    size_t ia2Size = 16;
    qsort(ia, ia + iaSize);
    printArray(ia, iaSize);
    qsortMulti(ia2, ia2 + ia2Size);
    printArray(ia2, ia2Size);
}

从上面的代码中可以清楚地看到我只是尝试实现相同的qsort函数,但是有多个线程。关于相关问题的堆栈溢出的其他问题和答案让我看到了这个版本的代码,这给我留下了一个非常简单的问题和相关的问题: 是什么导致多线程部分导致分段错误? 需要明确的是:我不需要任何人为我建立解决方案,我更倾向于指出或指示在哪里找到分段故障的来源,因为我没有看到它。提前谢谢!

1 个答案:

答案 0 :(得分:2)

为了使std::async返回std::future<T>类型的对象,传递给它的函数只需要返回T。例如:

int compute() { return 42; }
std::future<int> result = std::async(&compute);

在您的情况下,这意味着qsortMulti应该具有签名

void qsortMulti(int* beg, int* end);

并且不需要从中返回任何内容。在您提供的代码中,qsortMulti会返回std::future<void>本身,这会导致std::async返回std::future<std::future<void>>类型的对象,这可能不是您想要的。此外,您的函数仅在范围为空的情况下返回某些内容(位于顶部的if)。在所有其他代码路径中(例如,到达函数的末尾),您根本不返回任何内容,这会导致调用者访问未初始化的对象,这可能是seg错误的原因。