スレッド間での変数の共有と排他処理  ミューテックス(CreateMutex/OpenMutex API)

スレッド間で連携して処理をするには、連携するためタイミングをあわせる必要がある。
ミューテックスを使うと変数の競合を避けることができる。いわば踏切信号を作る方法だ。
第3回 マルチタスクに不可欠な同期の仕組みを学ぶ

2つのスレッドがある場合は両方がwhile句などで繰り返し処理をしているはず。
その間にある変数の旗にして処理することで連携するのだが、同時にその旗に書き込もうとすると問題だ。ミューテックスでロックを掛けることで競合を回避する。
 複数のプロセスがからむコードやスレッドを作るコードは一挙に高度になる。しかもデバッグがむずかしい。プログラマとしては腕の見せどころだ。難しいがなれれば簡単。あまり使わないから難しい。というかウィンドウを持つプログラムならイベントを使っうことでスレッドを作ることをしないからだ。

以下は、ミューテックスを使った例。flg変数を保護したければ以下の2つの行のコメンアウトを外す。
WaitForSingleObject (hMutex, INFINITE);
ReleaseMutex (hMutex);
mutex.c--------------------------------------
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <windows.h>
#include <process.h>

HANDLE hMutex, hThread;
int flg;

void
th (void *x)
{
  while (1)
    {
      Sleep (rand () / 1000);//乱数を使った待ち時間を不定にした
      printf ("%x flg:%d\n", GetCurrentThreadId (), flg);
      //WaitForSingleObject (hMutex, INFINITE);
      if(flg==1)flg = 0;
      //ReleaseMutex (hMutex);
    }

}


int
main (void)
{

  srand (time (NULL));		/* 時間で乱数の初期化 */

  hMutex = CreateMutex (NULL, FALSE, "mt");
  hThread = (HANDLE) _beginthread (th, 0, NULL);	//新しいスレッドを作る
  while (1)
    {
      Sleep (rand () / 1000);//乱数を使った待ち時間を不定にした
      printf ("%x flg:%d\n", GetCurrentThreadId (), flg);
      //WaitForSingleObject (hMutex, INFINITE);
      if(flg==0)flg = 1;
      //ReleaseMutex (hMutex);
    }

  return 0;
}
flg変数をスレッドごとで保護しなくても処理自体問題はない。しかし、flg変数を使って処理を結構長いコードで書いている場合は処理中に別のスレッドから書き込みがあったりするとflgの結果は不定だ。

C:\usr\lesson\opencv>cl mutex.c
Microsoft(R) 32-bit C/C++ Optimizing Compiler Version 15.00.30729.01 for 80x86
Copyright (C) Microsoft Corporation. All rights reserved.

mutex.c
Microsoft (R) Incremental Linker Version 9.00.30729.01
Copyright (C) Microsoft Corporation. All rights reserved.

/out:mutex.exe
mutex.obj

C:\usr\lesson\opencv>mutex
1018 flg:0
1018 flg:0
1018 flg:0
468 flg:0
468 flg:1
1018 flg:1
468 flg:0
1018 flg:1
468 flg:0
468 flg:1
468 flg:1
1018 flg:1
続く.....
「_beginthread ミューテックス」でグーグルするとサンプルがある。
名前:
コメント:
「今日の訪問数: -
「昨日の訪問数: -
「今までの訪問数: -
最終更新:2010年02月10日 01:28
ツールボックス

下から選んでください:

新しいページを作成する
ヘルプ / FAQ もご覧ください。