2016-04-22 13 views
0

私はLinuxの並行性とスレッドの概念について新しく、比較的簡単な問題を解決しようとしました。グローバル変数をインクリメントする同じ関数を実行する2つのスレッドを作成します。私は本当に私のプログラムから希望する代わりに、その変数をインクリメントすることで、つまり、画面に変数版画メッセージというインクリメントスレッドをステップごとに言うので、期待される出力は次のようになります。Linuxの並行性:クリティカルゾーンの2つのスレッドの代替アクセス

Thread 1 is incrementing variable count... count = 1 
Thread 2 is incrementing variable count... count = 2 
Thread 1 is incrementing variable count... count = 3 
Thread 2 is incrementing variable count... count = 4 

ので、に。

私は相互排他を保証セマフォと実装を試してみましたが、それにもかかわらず、結果はこのようになります。どのように行う

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

int count = 0; 
sem_t mutex; 

void function1(void *arg) 
{ 
     int i = 0; 
     int *a = (int*) arg; 

     while (i < 10) 
     { 
      sem_wait(&mutex); 
      count++; 
      i++; 
      printf("From the function : %d count is %d\n",*a,count); 
      sem_post(&mutex); 
     } 
} 

int main() 
{ 
    pthread_t t1,t2; 
    int a = 1; 
    int b = 2; 
    pthread_create(&t1,NULL,(void *)function1,&a); 
    pthread_create(&t2,NULL,(void *)function1,&b); 

    sem_init(&mutex,0,1); 
    pthread_join(t2,NULL); 
    pthread_join(t1,NULL); 
    sem_destroy(&mutex); 
    return 0; 
} 

私の大きな問題は今、:

Thread 2 is incrementing variable count... count = 1 
Thread 2 is incrementing variable count... count = 2 
Thread 2 is incrementing variable count... count = 3 
Thread 2 is incrementing variable count... count = 4 
Thread 2 is incrementing variable count... count = 5 
Thread 1 is incrementing variable count... count = 6 
Thread 1 is incrementing variable count... count = 7 
Thread 1 is incrementing variable count... count = 8 
Thread 1 is incrementing variable count... count = 9 
Thread 1 is incrementing variable count... count = 10 

私のコードは次のように見えます私はスレッド間のこの交替を達成する?私は相互排除を持っていますが、交代はまだありません。たぶん私はセマフォの使い方の良い洞察を欠いているかもしれませんが、誰かがそれを私に説明してくれれば非常に感謝しています。 (私はこのトピックに関するいくつかのコース、すなわちLinuxセマフォー、並行性とスレッドを読んでいますが、十分な情報がありませんでした)

答えて

0

mutexロックは公平性を保証しません。つまり、スレッド1がスレッド1を解放して再び獲得しようとすると、スレッド1がそのブロックで同時に実行できないという保証はありません。

編集:おそらく間違っていたので、以前のCスタイルの解決策を削除しました。質問は、同期ソリューションを要求します。

本当にこれを正しく実行したい場合は、モニターとガード(または条件変数)と呼ばれるものを使用します。あなたはそれでそれを行うにはどのように見てみる必要があるだろうので、私はCとpthreadとあまり慣れていないんだけど、Javaで、それは次のようになります。私は私のIDEでコードを書かれている

public class IncrementableInteger { 
    public int value; 

    @Override 
    public String toString() { 
     return String.valueOf(value); 
    } 
    } 

    @Test 
    public void testThreadAlternating() throws InterruptedException { 
    IncrementableInteger i = new IncrementableInteger(); 

    Monitor m = new Monitor(); 
    Monitor.Guard modIsZeroGuard = new Monitor.Guard(m) { 
     @Override public boolean isSatisfied() { 
     return i.value % 2 == 0; 
     } 
    }; 

    Monitor.Guard modIsOneGuard = new Monitor.Guard(m) { 
     @Override public boolean isSatisfied() { 
     return i.value % 2 == 1; 
     } 
    }; 

    Thread one = new Thread(() -> { 
     while (true) { 
     m.enterWhenUninterruptibly(modIsZeroGuard); 
     try { 
      if (i.value >= 10) return; 
      i.value++; 
      System.out.println("Thread 1 inc: " + String.valueOf(i)); 
     } finally { 
      m.leave(); 
     } 
     } 
    }); 

    Thread two = new Thread(() -> { 
     while (true) { 
     m.enterWhenUninterruptibly(modIsOneGuard); 
     try { 
      if (i.value >= 10) return; 
      i.value++; 
      System.out.println("Thread 2 inc: " + String.valueOf(i)); 
     } finally { 
      m.leave(); 
     } 
     } 
    }); 

    one.start(); 
    two.start(); 

    one.join(); 
    two.join(); 
    } 
+0

を、それ最初の印刷後に実際にブロックする – Dragos2795

+0

実際にブロックしているとは思わないので、最初のスレッドがmutexを絶え間なく取得している可能性があります。だから、もしあなたが "スレッド* aが走っている"というif文の外にプリントを追加するなら、それはそれがプリントアウトし続けるのを見るはずです。それはどうなるの? – Almog

関連する問題