2

Facade PatternAllegroのスレッドの使用をラップしたいと思います。つまりinstall_int_ex(void (__cdecl*)(void), int tick);remove_int(void (__cdecl*)(void))テンプレートを使用してuser-defined Functor Objects、クラスが作成および破棄されたときに割り込みをインストールおよび削除するために作成したクラスを使用します。

コンパイラエラーが発生し続けます:error C2664: 'install_int_ex' : cannot convert parameter 1 from 'void (__thiscall [User-defined FunctorName Here]::* )(void)' to 'void (__cdecl *)(void)'および同様のremove_int(void (__cdecl*)(void))

呼び出された関数がユーザーデータへのポインターを受け入れる場合、これは機能するようですvoid*

残念ながら、Allegroはこれほど柔軟ではありません。この制限を回避する方法はありますか、それともWindowsを使用する必要がありますかCreateThread(そしてプロセスで「実際の方法」のスレッド化を学ぶ必要がありますか)?

関連項目:スレッドのエントリポイント関数としてのC++メンバー関数の使用

4

2 に答える 2

4

これは実際には不可能です。これは期待される関数型です(無視し__cdeclます):

void (*)(void);

パラメータを取りません。これがC++の非静的メンバー関数である場合、暗黙のthisパラメーターがありますが、これはCです。パラメーター(暗黙のパラメーターを含む)を関数に渡したい場合はthis、この方法で行うことはできません。

グローバル変数を使用してファンクター(不良)を渡すか、代わりにスレッドを使用することができます。

でも、

install_int_exソース)のアレグロドキュメントに注意してください。

ただし、割り込みコンテキストで呼び出されるため、そこで実行できることには多くの制限が課せられることに注意してください。大量のスタックを使用したり、オペレーティングシステムを呼び出したり、Cライブラリ関数を使用したり、浮動小数点コードを含めたりしてはならず、非常に高速に実行する必要があります。

割り込みコンテキストは危険なものです。スレッド化と同じではありませ。C++コードの機能を理解するのが得意でない限り、C++コードを割り込みコンテキストに配置しないでください。

C++関数をに渡さないinstall_int_exでください。 (繰り返しますが、C ++コードを呼び出すライブラリが正確にわかっている場合を除きます。)

一般に、割り込みで実行されるコードをプログラムする方法を学ぶことは、マルチスレッドコードを書く方法を学ぶことよりも困難です。割り込みは、スレッドがそうではない方法でライブラリ関数に大混乱をもたらします。また、シグナルハンドラの微妙な間違いによって引き起こされる、よく知られたプログラムには多くのセキュリティホールとバグがあります。

于 2012-06-21T01:11:35.540 に答える
0

クラスAlarmFunctionObjectの非静的メンバー関数を渡します。メンバー関数を静的として宣言してみてください。実際のAlarmFunctionObjectにアクセスする必要がある場合は、そのスコープでアクセスできるオブジェクトで、非静的メンバー関数を呼び出す静的関数を渡す必要があります。

class AlarmFunctionObject
{
public:
    static void func()
    {
        someInstanceOfAlarmFunctionObject->myMemberAFunc();
    }
    void myMmberFunc()
    {
        // do stuff
    }
};

myMemberFuncの代わりにAlarmFunctionObject::funcを渡します

于 2012-06-21T00:54:43.307 に答える