2013-05-03 79 views
0

我希望4個線程將進入名爲read的同一個函數,並執行函數中的內容(在監視器上打印之後進行讀取,以及以顯示所有...)。 問題:多線程程序中的核心轉儲:basic_string :: _ S_construct null無效

terminate called after throwing an instance of 'std::logic_error' 
    what(): basic_string::_S_construct null not valid 
trAborted (core dumped) 

的代碼是:

#include <pthread.h> 
#include <unistd.h> 
#include <stdio.h> 
#include <iostream> 
#include <time.h> 
#include <cstdlib> 
#include <fstream> 
#include <string> 
using namespace std; 

struct v { 
    int id; 
    char* ad; 

    v(int a, char* t) { 
     id = a; 
     ad = t; 
    } 
}; 

int bank = 1000; 
pthread_mutex_t mutex; 

void* read(void* argument) 
{ 
    cout << "tr"; 
    v* d; 
    int num; 
    d = (v*) argument; 
    string l = d->ad; 
    int n = d->id; 
    string x = ""; 
    ifstream textfile; 
    textfile.open(l.c_str()); 
    while (!textfile.eof()) { 
     textfile >> x; 
     if (x == "SUB") { 
      pthread_mutex_lock(&mutex); 
      textfile >> num; 
      bank = bank - num; 
      cout << "person num " << n << " sub " << num << " dollars and know in the Bank: " << bank << endl; 
      pthread_mutex_unlock(&mutex); 
     } 
     if (x == "ADD") { 
      pthread_mutex_lock(&mutex); 
      textfile >> num; 
      bank = bank + num; 
      cout << "person num " << n << " add " << num << " dollars and know in the Bank: " << bank << endl; 
      pthread_mutex_unlock(&mutex); 
     } 
     if (x == "GET") { 
      pthread_mutex_lock(&mutex); 
      cout << "person num " << n << " look in the Bank: " << bank << endl; 
      pthread_mutex_unlock(&mutex); 
     } 


    } 
    textfile.close(); 
    return 0; 
} 

int main(void) 
{ 
    pthread_mutex_init(&mutex, NULL); 
    int i = 0, j = 0; 
    v data1(1, "file1.dat"), data2(2, "file2.dat"), data3(3, "file3.dat"), data4(4, "file4.dat"); 
    pthread_t t1, t2, t3, t4; 
    i = pthread_create(&t1, NULL, read, (void*)&data1); 
    if (i != 0) cout << "error" ; 
    j = pthread_create(&t2, NULL, read, (void*)&data2); 
    if (j != 0) cout << "error" ; 
    i = pthread_create(&t3, NULL, read, (void*)&data3); 
    if (i != 0) cout << "error" ; 
    j = pthread_create(&t4, NULL, read, (void*)&data4); 
    if (j != 0) cout << "error" ; 

    pthread_exit(NULL); 

    return 0; 
} 
+0

通過用try/catch連續包裝程序中越來越小的部分來做分而治之,直到找出哪個語句正在拋出。另外:什麼操作系統,編譯器,編譯器的版本號,也許最重要的是libc的版本?它可能不是答案,但在一些較舊的Gnu libcs​​中,字符串構造函數不是線程安全的(它們在實現中深處共享一個未同步的單例)。 – 2013-05-03 15:03:00

+1

請不要在覈心轉儲錯誤之前發佈問題,直到您告訴我們錯誤的行號。你真的希望我們爲你編譯和調試嗎?告訴我們哪一行是問題。 (如果你不知道該怎麼做,那麼在編寫超過10行的程序之前,請學會使用gdb,運行「gdb ./myprog」,並在使用堆棧跟蹤調用終止時停止。) – 2013-05-03 17:00:41

+0

@NicholasWilson:我同意(我們需要行號),但這是一個未捕獲的異常,所以在終止時堆棧已經完全解除。那麼gdb會給出任何有用的信息?這就是爲什麼我提出了分而治之的嘗試捕捉方法。 – 2013-05-03 17:48:38

回答

1

你傳遞棧,這是幾乎從來沒有一個好主意,你的線程的數據。

當您調用pthread_exit時,主線程的堆棧(包含dataN對象)被釋放。如果其中一個線程在pthread_exit之後安排,它將在解除分配的對象上運行。

最好的解決方案是通過new在堆上分配您的data對象。

+0

更好的是:在調用'pthread_exit()'之前,在每個子線程上調用'pthread_join()'。 – 2013-05-03 19:34:44