4

事前定義されたクラス/関数の事前定義された .lib ファイルが与えられます。

次のものを作成する必要があります。

    Cdefined *p = new Cdefined;
    p->Init();

main() プログラムで、スレッドを呼び出す前にクラス オブジェクトを初期化します。

ただし、各スレッドで次のように呼び出す必要があることに気付きました。

    p->doProcess(); 

スレッドごとにコードのセグメントを実行します。

ただし、この関数は、私が呼び出さない限り機能しませんp->Init()

現在、p の少なくとも 2 つのスコープ (1 つは で作成されmain()、そのうちの N は N スレッドで作成) を持っているので、スコープ エラーなしでクラスを渡すことができるように、スレッドを設計するにはどうすればよいでしょうか? [私の制約は、それp->Init()を呼び出す必要があることですmain()]

4

2 に答える 2

4

オブジェクトの有効期間が単に のスコープにバインドされている場合main、それは簡単です。オブジェクトを破棄する前に、すべてのスレッドを停止して結合したことを確認してください。これは、スコープ内のスマート ポインターを使用してオブジェクトを管理するmainか、より簡単に、オブジェクトに自動有効期間を与えることによって、より適切に適用できmainます。

void thread_func(Cdefine *);

int main()
{
    Cdefine thing;
    thing.Init();

    std::thread thread1(thread_func, &thing);
    std::thread thread2(thread_func, &thing);

    // do stuff

    thread1.join();
    thread2.join();

    // Now it's safe to destroy the object
}

オブジェクトをスレッドのスコープよりも広いスコープに単純にバインドできない、より複雑な状況では、std::shared_ptr(またはstd::tr1::shared_ptr2011boost::shared_ptr年より前の言語で立ち往生している場合は) オブジェクトを管理することを検討できます。例えば:

void thread_func(std::shared_ptr<Cdefine> p);

void spawn_threads()
{
    std::shared_ptr<Cdefine> p = std::make_shared<Cdefine>();
    p->Init();

    std::thread thread1(thread_func, p);
    std::thread thread2(thread_func, p);

    thread1.detach();
    thread2.detach();

    // The threads can carry on doing their thing, and it's safe to
    // drop our shared pointer. The object will be deleted when the
    // last thread drops its pointer to it.
}

余談ですがInit、オブジェクトを構築した後に関数を呼び出す必要があるのはなぜですか? それがコンストラクターの目的であるため、コンストラクターで初期化しないのはなぜですか?

于 2012-06-14T10:57:44.007 に答える
1

Cdefinedスレッドごとに のインスタンスを 1 つ作成し、そのInitメソッドを呼び出して、引数としてスレッドに渡します。

何かのようなもの:

for (int i = 0; i < NUM_THREADS; i++)
{
    Cdefined *p = new Cdefined;
    p->Init();
    create_thread(thread_func, p);
}

そして、スレッド関数:

void *thread_func(void *data)
{
    Cdefine *p = reinterpret_cast<Cdefine*>(data);

    for (;;)
    {
        // Do stuff...
        p->doProcess();
        // Do other stuff
    }

    return 0;
}
于 2012-06-14T10:17:40.443 に答える