2011-03-25 51 views
0

我有這樣的家庭作業的學校 - 我完成它發送,並得到0%:] ... 所以我想問一下,如果我的想法是正確的。例如,如果我想用線程編寫程序 - 我必須調用50次thrute,並有5個線程可用(我必須儘可能使用它們)。你能告訴我,如果我做錯了什麼 - 我想我是因爲printf說我只使用一個線程?我不太確定我會做這件事的方法。POSIX - 旗語,互斥線程Ç

在此先感謝 尼古拉JISA

這裏是我的源代碼:

#include <stdio.h> 
#include <stdlib.h> 
#include <pthread.h> 
#include <semaphore.h> 

#define THREADS 5 
#define CYCLES 50 

sem_t sem1; 
pthread_mutex_t m1, m2; 
long int result = 0; 
int thread_status[THREADS]; // status of threads, value -1 for working thread, other values for free threads 

typedef struct Arg { 
    long int number; 
    int thread_ID; } ARG; 

void * thrfunction (void * arg) { 
    int number = ((ARG *) arg)->number, thread_ID = ((ARG *) arg)->thread_ID, i; 
    thread_status[thread_ID] = -1; 
    pthread_mutex_unlock (& m1); 
    for (i = 0; i < number; i ++); 
    pthread_mutex_lock (& m2); 
    result = result + number; 
    printf ("Thread %d result = %ld\n", thread_ID, result); 
    pthread_mutex_unlock (& m2); 
    pthread_mutex_lock (& m1); 
    thread_status[thread_ID] = thread_ID; 
    sem_post (& sem1); 
    pthread_mutex_unlock (& m1); 
    return NULL; } 

int main (int argc, char * argv[]) { 
    pthread_t thr[THREADS]; 
    pthread_attr_t Attr; pthread_attr_init (& Attr); pthread_attr_setdetachstate (& Attr, PTHREAD_CREATE_JOINABLE); 
    pthread_mutex_init (& m1, NULL); pthread_mutex_init (& m2, NULL); 
    sem_init (& sem1, 0, THREADS); 

    int i, j; 
    ARG * pom = (ARG *) malloc (sizeof (* pom)); 

    for (i = 0; i < THREADS; i ++) 
     thread_status[i] = i; 

    for (i = 0; i < CYCLES; i ++) { 
     pom->number = rand() % 100000 * 10000; 
     sem_wait (& sem1); 
     pthread_mutex_lock (& m1); 
     for (j = 0 ; j == -1; j ++); 
      pthread_create (& thr[j], & Attr, thrfunction, (void *) pom); } 
    free (pom); 
    pthread_attr_destroy (& Attr); pthread_mutex_destroy (& m1); pthread_mutex_destroy (& m2); sem_destroy (& sem1); 
    for (i = 0; i < THREADS; i ++) 
     pthread_join (thr[i], NULL); 
    return 0;} 
+0

你相信下面的代碼? 「for(j = 0; j == -1; j ++); pthread_create(&thr [j],&Attr,thrfunction,(void *)pom);」 – Srikanth 2011-03-25 21:47:34

+0

我也這麼認爲......但我對這個POSIX編程非常新鮮...... – 2011-03-25 22:07:40

+0

好點Srikanth。尼古拉斯,你期望多少次(j = 0; j == -1; j ++);運行,你期望它做什麼?如果是時序循環,這是一個非常糟糕的主意。如果C編譯器選擇,則允許它完全移除該循環。 – 2011-03-25 22:44:50

回答

2

,我看到的第一個問題是,你正在使用的鎖過於頻繁

線程比順序編程效率要低得多,如果你所有的程序做的是採取鎖。鎖定需要花費時間來執行和釋放。這段時間是從你的程序應該做的工作中拿走的。

第二個問題,我看到的是,你的for環路thrfunction什麼都不做。它計數我從0到數字?這就是它所做的一切?

我看到的第三個問題是您撥打free(pom)並在創建完所有線程後致電pthread_mutex_destroy不好!線程仍在使用它!您無法保證線程甚至在此時開始運行。您的操作系統可能需要幾秒鐘甚至幾分鐘的時間(如果內存不足並交換到磁盤)才能開始運行您創建的所有線程。

有些事情,你可能會發現想想線程有用的是寫下每一個「關鍵部分」,鎖具之間的片,月卡,或使用任何移動來表示這些作品。爲每個線程製作一張卡片或片段。除非鎖,連接,信號燈或其他任何東西阻止它們,否則這些塊可以在時間軸上向上或向下移動。如果你想獲得真正的技術,編譯器優化和處理器亂序執行甚至可以在限制範圍內重新排列片斷執行順序。

一些程序(不是你的)可能看起來像以下(和怎麼看待線程在鎖步驟7減慢至單速):

   0 <- parent process spawns threads 
       1 <- parent process calls join to wait for thread in first column. 
2 2 2 
3  3 
4 3 4 
5  5 2 
6  6 3 
      4 
      5 
      6 
7 4 7 7 <-- step 7 waits for lock 
    5 8 
    6 9 
    7 10 
     11  <- step 11 releases lock 
8 
9 
10 
11 
    8 
    9 
    10 
    11 
      8 
      9 
      10 
      11 
12 12 12 12 
13 13 13 13 
14 14 14 14 <- step 14 each thread returns. 
       15 <- parent process wait on thread 1 succeeds. 
       16 <- wait for thread 2 
       17 <- wait for thread 3 
       18 <- wait for thread 4 
       19 <- parent now cleans up thread data, lock data. 
       20 <- parent exits. 
+0

感謝您的時間 – 2011-03-25 22:01:36