0

だから私は次のようなクラスを持っています:

class mySafeData
{
public:
    void Set(int i) {
        boost::mutex::scoped_lock lock(myMutex);
        myData = i;
    }
    void Get( int& i)
    {
        boost::mutex::scoped_lock lock(myMutex);
        i = myData;
    }
private:
    int myData;
    boost::mutex myMutex;

};

ループで呼び出すSetスレッドと、ループで呼び出す3つのスレッドがGetあります。私は自分のスレッドをGet1回だけデータの平和にする必要があります(つまりGet、私たちほど速く呼び出すことはできずSet、それは問題ありませんが、新しいものが呼び出されたときに2回以上呼び出すことはできませんSet)。つまり、スレッドが呼び出された後、それはunteelにGetアクセスできなくなります。そのようなものをそのような単純なクラスに実装する方法、または私のロックはデフォルトでそれを行いますか?GetSet

4

2 に答える 2

2

条件変数が必要です。

リーダースレッドが条件変数に関連付けられたミューテックスを取得する場合でも、条件が満たされていることを確認する必要があることに注意してください。おそらく、セッターが何かを設定したときにフラグを設定し、リーダーがそれを読み取ったときにそれをリセットできるようにします。

これには改良が必要ですが、うまくいきます。私は通常、std :: dequeを使用するので、ライターはロックする必要がありますが、スレッドがそれを読み取るのを待つ必要はありません。

class mySafeData
{
public:
  mySafeData() : myData(0), changed( false )
  {
  }

  void Set(int i) 
  {
    boost::mutex::scoped_lock lock(myMutex);
    while( changed )
        myCondvar.wait( lock ); // wait for the data to be read

    myData = i; // set the data
    changed = true; // mark as changed
    myCondvar.notify_one(); // notify so a reader can process it
  }

  void Get( int& i)
  {
    boost::mutex::scoped_lock lock(myMutex);
    while( !changed )
    {
       myCondvar.wait( lock );
    } 
    i = myData;
    changed = false; // mark as read
    myCondvar.notify_one(); // notify so the writer can write if necessary
  }
 private:
   int myData;
   boost::mutex myMutex;
   boost::condition_variable myCondvar;
   bool changed;
};
于 2011-01-17T12:11:11.057 に答える
1

オブジェクトの状態の変化を他のスレッドに通知するには、条件変数を使用する必要があります。

于 2011-01-17T12:09:19.807 に答える