2017-09-13 49 views
0

嘿,我是新来的c + +,我试图创建一个多线程合并排序,但我一直得到这个错误。 *当数组为1000整数时,线程合并排序似乎可行,但是当我将数组初始化为更大的数字(如10000整数)时,它给了我这样的例外:“终止调用时没有激活的异常” 您的帮助将会很多不胜感激! 以下是我的代码:终止调用没有一个活动的异常(多线程合并排序)

#include <iostream> 
#include <stdio.h> 
#include <stdlib.h> 
#include <time.h> 
#include <thread> 
#include <pthread.h> 
#include <ctime>// include this header 

using namespace std; 


void shuffle(int *arr, size_t n) 
{ 
    if (n > 1) 
    { 
     size_t i; 
     srand(time(NULL)); 
     for (i = 0; i < n - 1; i++) 
     { 
      size_t j = i + rand()/(RAND_MAX/(n - i) + 1); 
      int t = arr[j]; 
      arr[j] = arr[i]; 
      arr[i] = t; 
     } 
    } 
} 


// A function to merge the two half into a sorted data. 
void merge(int *a, int low, int high, int mid) 
{ 
    // We have low to mid and mid+1 to high already sorted. 
    int i, j, k, temp[high-low+1]; 
    i = low; 
    k = 0; 
    j = mid + 1; 

    // Merge the two parts into temp[]. 
    while (i <= mid && j <= high) 
    { 
     if (a[i] < a[j]) 
     { 
      temp[k] = a[i]; 
      k++; 
      i++; 
     } 
     else 
     { 
      temp[k] = a[j]; 
      k++; 
      j++; 
     } 
    } 

    // Insert all the remaining values from i to mid into temp[]. 
    while (i <= mid) 
    { 
     temp[k] = a[i]; 
     k++; 
     i++; 
    } 

    // Insert all the remaining values from j to high into temp[]. 
    while (j <= high) 
    { 
     temp[k] = a[j]; 
     k++; 
     j++; 
    } 


    // Assign sorted data stored in temp[] to a[]. 
    for (i = low; i <= high; i++) 
    { 
     a[i] = temp[i-low]; 
    } 
} 

void mergeSort(int A[], int low, int high){ 

     if (low < high) { 
     int mid = (low + high)/2; 
     thread sort_thread1(mergeSort,std::ref(A),low,mid); 
     thread sort_thread2(mergeSort,std::ref (A), mid + 1, high); 
     sort_thread1.join(); 
     sort_thread2.join(); 
     merge(A, low, high, mid); 
    } 
    return; 
} 
int main(){ 

    int size =10000; 
    int A[size]; 
    for (int i=0; i<size; i++){ 
     A[i] = i; 
    } 
    shuffle(A, size); 
    //for (int i=0; i<size; i++){// 
     // printf("%d ", A[i]); 
    //}// 
    int low = 0; 
    int high = size-1; 
    int start_s=clock(); 
    // the code you wish to time goes here 
    mergeSort(A,low,high); 

    int stop_s=clock(); 
    cout << "time: " << (stop_s-start_s)/double(CLOCKS_PER_SEC) << endl; 

    //for(int i = 0; i<size;i++){ 
     //cout << A[i] << endl;` 
    //} 
    return 0; 

} 
+2

通过您的代码行与调试器步进当行什么你有没有注意到? – user0042

+0

'std :: ref(A)'看起来不正确。你坚持使用引用,所以你不应该需要它。 – NathanOliver

+0

@ user0042我在windows上使用geany,我不认为Geany允许调试模式。 – Moi

回答

1

此代码创建的线程太多。

当它无法创建更多线程std::thread构造函数抛出异常。异常开始展开堆栈,调用现有的std::thread对象的析构函数。 std::thread::~thread destructor is problematic because it calls std::terminate if the thread is joinable but has not been joined

查看Discussion about std::thread and RAII了解更多详情。

一种用于此代码解决将是:

  • 保留当前线程忙排序,而不是等待在其它2个线程,因此减半的线程数。
  • 对小数组进行排序而不创建新线程。

例子:

void mergeSort(int A[], int low, int high) { 
    if (low < high) { 
     int mid = (low + high)/2; 
     if(high - mid > 500) { 
      thread sort_thread1(mergeSort,std::ref(A), low, mid); 
      mergeSort(A, mid + 1, high); // Keep this thread busy. 
      sort_thread1.join(); 
     } 
     else { // Sort small arrays using 1 thread only. 
      mergeSort(A, low, mid); 
      mergeSort(A, mid + 1, high); 
     } 
     merge(A, low, high, mid); 
    } 
} 
相关问题