クロスプラットフォームのマルチスレッドアプリケーションを作成する際には、状況を考慮してください。クロスプラットフォームコードで抽象クラスのインスタンスを使用
これを実行すると、おそらくプラットフォームの機能をいくつかのクラスに分けることになります。たとえば、アプリケーションにテキストを出力するには、単純なコンソールが必要です。可能な方法は、いくつかの抽象クラスConsole
を宣言することです。これは、あるプラットフォームでそれを必要とするときに継承し、派生クラスのインスタンスを使用します。
Console
インスタンスがどこかに必要であることが分かるまで(たとえば、クラスメンバーとして)すべてが問題ありません。他のクラスでクラスConsole
のメンバ変数を宣言しようとすると、抽象クラスのインスタンスが許可されていないため、エラーが発生することになります。しかし、コンパイル時に、派生クラスが実装され、正しいことが考えられますが、そのクラスの名前がわからない場合や、プラットフォームによって異なる名前がある場合もあります。
ここは複雑な例です。
クロスプラットフォームのマルチスレッドアプリケーションを開発する場合は、Syncer
(シンクロナイザー)のようなものが必要です。それのアナログはWindows APIのmutexオブジェクトです。
プラットフォームによっては、クラスが異なることがわかります。しかし、プラットフォームの変種にはいくつかの方法があることは知っています。例えば、これらの方法はlock
とunlock
です。あなたは、これらのメソッドが実行されるのか分からないので、あなたは次のように純粋仮想それらを宣言します。
class Syncer
{
public:
virtual void lock()=0;
virtual void unlock()=0;
}
そして今、いくつかのクラスを開発し、あなたがものをする必要はないことを、実感が、このSyncer
の多く-s。しかし、クラスは抽象クラスなので、それを行うことはできません。
私が見つけた可能な解決策は以下のとおりです。
1)は、テンプレートを使用してください。たとえば:
template<class syncer>
class SyncUser
{
public:
syncer syncInstance;
SyncUser()
{
syncInstance().lock;
}
しかし、問題は、クラスのユーザーがsyncer
パラメータの代わりに他のクラスを貼り付けることである(彼はあるいは、問題ではないではないだろうだろう。彼はこれを行うことができます。)。。そのソリューションは、一般的なソリューションが期待されるほど良くはありません。
2)マクロを使用します。この方法を使用している場合、Syncer.h
の内容は、次のようになる:"platform1_sync_implement.h"
ファイルには、次のを持っている場合
class Syncer
{
public:
virtual void lock()=0;
virtual void unlock()=0;
}
#ifdef PLATFORM1
#include "platform1_sync_implement.h"
#else
#include "platform2_sync_implement.h"
#endif
:今
#include "Syncer.h"
class SyncPlatform1 : public Syncer
{
//Correct implementation
}
#define Syncer SyncPlatform1
、誰もがSyncer.h
を含ま実装したバージョンを持っているでしょう。 しかし、この方法は、また、Sync
抽象化が実装されるプラットフォームのリストを必要とするので、良くありません。大きなプロジェクトではそれほど良いことではありません。クラスを宣言し、他のプログラマーがそれを使うことができるかどうかを気にするだけです。
したがって、問題は、抽象クラスのインスタンスをどこかで実装することができるということを知っているということです。
P.S:それはそのような質問のための最良の名前ではないことを知っています。 P.P.S .:悪い英語を申し訳ありません。
tl; dr。短い答えです "抽象クラスのインスタンス"はありません。定義では、抽象クラスはインスタンス化できません – user463035818
私はあなたの動機付けによって確信していません。バーチャルファンクション多相は、実行時に異なる実装*を扱うためのものです。複数のプラットフォームをサポートするユースケースでは、実行時の決定がないようです。あなたのプログラムは、ゲームボーイとプレイステーションで同時に*実行されていません。むしろ、各プラットフォーム用に再コンパイルします。 –
実際には、別のクラスのメンバとして抽象クラスから派生したオブジェクトが必要な場合は、その抽象クラスへのポインタをメンバとして持つことができます。 – user463035818