2010-12-13 1 views
3

を経由してロック、ロックはクラスクリティカルセクションやミューテックス所有している構図を介して達成される:私が書いたり見直されているほとんどのコードでは、継承ではなく合成

class MyClass 
{ 
    Mutex mMutex; 
}; 

と可変メンバが潜在的に可能に

:私はこのように、コードを継承経由でロック実装されたいくつかのコードを見直し

void MyClass::Method() 
{ 
    Lock lock(mMutex); 
    // ... 
} 

今日:複数のスレッドを介してアクセス、我々が取得し、このようにRAIIを経由してロックを解除します

class MyClass : public Mutex 
{ 
    // ... 
}; 

とロックは、クラスのロック「そのもの」によって行われる。

void MyClass::Method() 
{ 
    Lock lock(this); 
    // ... 
} 

このアプローチのいずれかの利点や欠点はありますか?それとも単なるスタイルの問題ですか?

+0

特に、「継承されたミューテックス」の部分で、より具体的に説明する必要があります。それはインターフェイスまたは実際の同期オブジェクトから継承されましたか? – YeenFei

+0

@ YeenFei - 実際の(つまり具体的な)同期オブジェクトから継承されました。 – LeopardSkinPillBoxHat

答えて

4

プライベート継承は、このために少しより多くの意味を作るかもしれません。しかし、私はMutexから継承する必要がなければ(Mutexにアクセスする必要のある保護されたメンバーがあったように)、メンバーにするより標準的な構成のアプローチは、おそらく継承がなぜメンバーはMutexの代わりに使用されます)。

何らかの理由でクライアントがそのオブジェクトをロックできるようにする場合は、MyClassMutexとして扱うことができます。オブジェクトが予期しない方法でロックされていると、デッドロックの機会が増えるため、これは素晴らしい設計方法ではありません。 Mutexがプライベートのままである場合(継承または標準構成によるかどうかにかかわらず)、クラスはロックがどのように使用されているかをより確かめることができます。

このデザインを導入した人が.NETの影響を受けていてオブジェクトがロック可能な場合、私は驚くことはありません。 .NETではそれはlock(this)に共通していましたが、そのイディオムは不利になりましたが、今はロックに使用する特定のプライベートオブジェクトメンバーを持つ方が正しいと考えられます。

6

これはほとんど意味をなさない。 MyClassMutexを拡張する何らかの種類の同期オブジェクトですか?そうでなければ、MyClassMutexMyClassMutexの関係は「is-a」関係ではない)として使用することは意味をなさないので、継承はほとんど間違いの選択であることは間違いありません。

それはまた危険だ:プライベート継承が組成物を実装するために、多かれ少なかれ方法ですので、

MyClass x; 
Lock lock(x); 
x.Method(); // uh oh. 
+0

Win32の世界では、スレッドはロックを何度も取ることができるので、 "ああ"はありません。これはロックに賢明なアプローチであるように思われますが、それは私が慣れていたものである可能性があります。 –

+2

@マイケル:いくつかのプラットフォーム/スレッドライブラリには "Mutex"と "RecursiveMutex"の両方があり、スレッドが再度Mutexをロックすると、それ自体がデッドロックします。これが一般的なアプローチかどうかはわかりません。 –

関連する問題