【问题标题】:c++ waiting for thread exitc++等待线程退出
【发布时间】:2011-07-12 18:16:38
【问题描述】:

我在 Linux 下用 C++ 编写了一个程序。对于线程,我使用的是 pthread。 在程序中,我启动线程并且该线程一直在运行,直到我调用该函数,这应该停止它。在这里你可以看到我的代码。

bool isRunning = false;
pthread_t thread;

void startThread() {
    isRunning = true;
    int thread_return = pthread_create(&thread, NULL, runThread, NULL);
}

bool stopThread() {
    isRunning = false;
    // wait until the thread will be finished
    return true;
}

void* runThread(void* ptr) {
    while(isRunning) {
        // do smth.
    }
    pthread_exit(NULL);
}

当线程启动时,它会做某事。直到isRunning 的值变为false 并且主程序本身将执行其他操作。问题是,当我调用函数stopThread 时,该函数只是将isRunning 设置为false,而不是等到线程在while 循环中完成其任务。 我的问题是,我怎么能说函数stopThread,它应该等待线程退出。

在将isRunning 设置为false 后,我尝试将pthread_join 放入stopThread 函数中。但有时它会导致问题,即程序无限等待。因为线程完成的速度比程序来等待线程快。因为线程可以在while循环内的不同部分。所以我永远不知道线程需要退出多少。

谢谢

【问题讨论】:

    标签: c++ multithreading termination


    【解决方案1】:

    根据我对您问题的理解,您应该使用thread joining 的概念。

    这样,

    bool stopThread() {
        int returnCode;
        isRunning = false;
        void *status;
        rc = pthread_join(your_thread, &status);
    
        // wait until the thread will be finished
    
        if (rc) {
            printf("ERROR; return code from pthread_join() 
                    is %d\n", rc);
            exit(-1);
        }
        printf("Main: completed join with thread %ld having a status   
                of %ld\n",t,(long)status);
    
        return true;
    }
    

    【讨论】:

      【解决方案2】:

      查看函数pthread_joinSingle UNIX specification documentation for pthread_join.

      您需要跟踪线程 ID,才能使用此功能。一个常见的范例似乎是有一个 Thread 类,它封装了这些信息。

      【讨论】:

        【解决方案3】:

        在这种情况下,您应该可以对其执行pthread_join(),但如果由于某种原因不起作用,您可以尝试添加hasFinished 变量(然后在您关闭的任何地方等待hasFinished == true线程...)

        bool isRunning = false;
        pthread_t thread;
        
        // TODO FIX: this is a workaround due to pthread_join() not working properly
        bool hasFinished = false
        
        void startThread() {
            isRunning = true;
            int thread_return = pthread_create(&thread, NULL, runThread, NULL);
        }
        
        bool stopThread() {
            isRunning = false;
            // wait until the thread will be finished
            return true;
        }
        
        void* runThread(void* ptr) {
            while(isRunning) {
                // do smth.
            }
        
            // TODO FIX: this is a workaround because pthread_join() is not working properly
            hasFinished = true;
            pthread_exit(NULL);
        
        }
        

        [编辑澄清:]

        以及在哪里停止线程

        /**/
        // TODO FIX: this following is a workaround due to pthread_join() not working
        isRunning = false;
        
        int TimeoutSleep_ms = 100;
        // TimeoutSleep_ms * TimeoutCounter is the timeout time, 10 sec for this case
        int TimeoutCounter = 100; 
        
        while (!hasFinished && (--TimeoutCounter > 0))
            sleep(100);
        // END TODO FIX
        /**/
        

        【讨论】:

        • 作为旁白/澄清:在这种特殊情况下,假设我有时间,我会选择 pthread_join 和/或找出 pthread_join 不起作用的原因。这是一个几乎可以在任何线程情况下使用的习语,这就是我想给出它的原因。
        • @0A0D 关键在于,在您发出线程停止信号的代码中,您可以通过一种方式向您发出信号,表明您实际上已经停止了......例如在线程停止代码isRunning = false; while (!hasFinished /* && some timeout condition */); 或可能while (!hasFinished /* && some timeout condition */) sleep(100); 或类似的东西中,这样你就不会吃掉处理器。 (我将编辑回复以包含)
        • @0A0D 这就是为什么我在回答的第一句话中说“如果由于某种原因不起作用”。
        • 我还是觉得没用,长此以往会造成混乱。
        • 不管怎样,坏代码就是坏代码。顺便说一句,自从他接受了我的回答后,它一定是有效的。
        猜你喜欢
        • 2021-01-25
        • 1970-01-01
        • 2015-03-31
        • 2021-09-24
        • 1970-01-01
        • 1970-01-01
        • 2011-06-02
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多