0

基本的に GUI と、メイン プログラムの実行とオブジェクトの作成を担当する関数を備えたアプリケーションがあります。

現在、バックグラウンド作業が完了するとバックグラウンド作業が多すぎるため、GUI がクラッシュし、再び生き返ります。

ワーカー スレッドを作成する必要があります (私の GUI は何が起こっているかの進行状況を表示するだけなので、インターフェイス スレッドは必要ありません)。ワーカー スレッドが関数を実行し、他のワーカー スレッドが GUI を実行します。

これに関する情報を見つけるのに苦労しています。Google は役に立たないようです。役に立つ情報を教えてもらえますか? 現時点では、次のようなものがあります。

void __fastcall TfrmRunning::FormCreate(TObject *Sender)
{
   //Does most of my background stuff when this form is created
}
4

2 に答える 2

2

Threadz は、特に C++ Builder で使用できます。GUI通信が必要ない場合。GUI通信の問題についてSOにアドバイスを求めなければなりませんでした-メッセージを処理するためにマクロが必要で、間違ったフォームクラスを提供していました-スタックオーバーフローが発生しました:)

「クラス」には、Delphi に似た TThread クラスがあります。'Execute' をオーバーライドして、スレッド コードの実行を取得します。例:

class TpoolThread : public TThread{
    CBthreadPool *FmyPool;
protected:
     virtual void __fastcall Execute(void);
public:
    TpoolThread(CBthreadPool *myPool):TThread(true){
        FmyPool=myPool;
        Resume();
    };
};

TThread クラスがない場合 (私は C++ Builder 2009 を持っています - 以前のことはわかりません)、@inkooboo の提案に従って API 呼び出しに頼ることができます。WINAPI CreateThread() は単純な C スタイルの関数または静的メソッドのみを呼び出すため、通常、スレッド コードからインスタンス メソッドを呼び出すには、インスタンス (通常は「this」) を CreateThread パラメーターとして明示的に渡す必要があります。CreateThread API を使用した ThreadPool の例 (ただし、STL がある場合は、TThread もあると確信しています):

#ifndef cthreadpoolH
#define cthreadpoolH

#include <Classes.hpp>
#include <deque.h>

class ThreadPool;

class PoolTask {
friend class ThreadPool;
    TNotifyEvent FonComplete;
protected:
    ThreadPool *myPool;
    int param;
public:
    PoolTask(int inParam, TNotifyEvent OnDone):param(inParam),FonComplete(OnDone){};
    virtual void run()=0;
};

template <typename T> class PCSqueue{
    CRITICAL_SECTION access;
    deque<T> *objectQueue;
    HANDLE queueSema;
public:
    PCSqueue(){
        objectQueue=new deque<T>;
        InitializeCriticalSection(&access);
        queueSema=CreateSemaphore(NULL,0,MAXINT,NULL);
    };
    void push(T ref){
        EnterCriticalSection(&access);
        objectQueue->push_front(ref);
        LeaveCriticalSection(&access);
        ReleaseSemaphore(queueSema,1,NULL);
    };
    bool pop(T *ref,DWORD timeout){
        if (WAIT_OBJECT_0==WaitForSingleObject(queueSema,timeout)) {
            EnterCriticalSection(&access);
            *ref=objectQueue->back();
            objectQueue->pop_back();
            LeaveCriticalSection(&access);
            return(true);
        }
        else
            return(false);
    };
};

class ThreadPool {
    int FthreadCount;
    PCSqueue<PoolTask*> queue;
public:
    ThreadPool(int initThreads){
        for(FthreadCount=0;FthreadCount!=initThreads;FthreadCount++){
            CreateThread(NULL,0,staticThreadRun,this,0,0);
        };
    }
    void setThreadCount(int newCount){
        while(FthreadCount<newCount){
            CreateThread(NULL,0,staticThreadRun,this,0,0);
            FthreadCount++;
        };
        while(FthreadCount>newCount){
            queue.push((PoolTask*)NULL);
            FthreadCount--;
        };
    }
    static DWORD _stdcall staticThreadRun(void *param){
        ThreadPool *myPool=(ThreadPool*)param;
        PoolTask *thisTask;
        SetThreadPriority(GetCurrentThread(),THREAD_PRIORITY_BELOW_NORMAL);
        while (myPool->queue.pop(&thisTask,INFINITE)){
            if(thisTask==NULL){return(0);};
            thisTask->run();
            if (thisTask->FonComplete!=NULL) {
                thisTask->FonComplete((TObject*)thisTask);
            }
        }
    }
    void submit(PoolTask *aTask){
        aTask->myPool=this;
        queue.push(aTask);
    };
};

#endif
于 2012-07-18T08:19:27.343 に答える
0

WinAPIスレッド化機能、またはboost / C++11 threading librarypthread、その他などのスレッド化ライブラリを使用できます。

C++ のマルチスレッドへようこそ!

于 2012-07-18T07:51:08.780 に答える