Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/149.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
停止类方法在线程中运行 我创建了一个名为TimeC++的C++类,它有3种方法: 开始() 停止() 打印()_C++_Multithreading - Fatal编程技术网

停止类方法在线程中运行 我创建了一个名为TimeC++的C++类,它有3种方法: 开始() 停止() 打印()

停止类方法在线程中运行 我创建了一个名为TimeC++的C++类,它有3种方法: 开始() 停止() 打印(),c++,multithreading,C++,Multithreading,start()方法启用名为run的标志,将其值设置为true 使用stop()方法,禁用该标志,将其值设置为false print()方法在run==true的条件下执行while(),并在半秒钟内打印一些文本 定时器.hpp #ifndef TIMER #define TIMER 1 #include <iostream> #include <cstdbool> #include <unistd.h> class Timer{ private:

start()
方法启用名为
run
的标志,将其值设置为
true

使用
stop()
方法,禁用该标志,将其值设置为
false

print()
方法在
run==true
的条件下执行
while()
,并在半秒钟内打印一些文本


定时器.hpp

#ifndef TIMER
#define TIMER 1

#include <iostream>
#include <cstdbool>

#include <unistd.h>

class Timer{
private:
    bool run;

public:
    void start();
    void stop();
    void print();

};

#endif
#include "Timer.hpp"

void Timer::start(){
    this->run = true;
    this->print();
    return;
}

void Timer::stop(){
    this->run = false;
    return;
}

void Timer::print(){

    int counter = 0;

    while(this->run == true){

        std::cout << counter << std::endl;
        counter++;

        usleep(500000);
    }

    return;
}
#include <pthread.h>

#include "Timer.hpp"

void *handler(void *argument){

    ((Timer *) argument)->start();

    return argument;
}

int main(void){

    Timer *timer = new Timer();
    pthread_t timer_thread;
    int mainCounter = 0;

    pthread_create(&timer_thread, NULL, handler, (void *) &timer);

    while(true){

        if(mainCounter == 100){
            std::cout << "Stopping..." << std::endl;
            timer->stop();
        }

        std::cout << " => " << mainCounter << std::endl;
        mainCounter++;

        usleep(50000);
    }

    return 0;
}
输出为:

9
 => 90
 => 91
 => 92
 => 93
 => 94
 => 95
 => 96
 => 97
 => 98
 => 99
10
Stopping...
 => 100
 => 101
 => 102
 => 103
 => 104
 => 105
 => 106
 => 107
 => 108
 => 109
11


正如@user4581301所提到的,这将解决问题:

pthread\u创建(&timer\u线程,NULL,处理程序,(void*)&timer)

应该是

pthread\u创建(&timer\u线程,NULL,handler,(void*)timer)

问题是
timer
指向分配的
timer
类,而
&timer
指向堆栈上的某个地方。运行线程时,您试图访问
run
类成员,但由于
指向堆栈,因此实际读取的值不正确


其他注意事项:将
bool-run
声明为
std::atomic\u-bool-run
,或者使用任何互斥机制来实现线程安全。另外,始终删除分配的变量:
delete timer

如果要从多个线程读取和写入变量(例如
run
boolean变量),则需要使用互斥锁保护对该变量的所有访问,或者使用
std::atomic
使变量成为原子变量。否则,您将调用未定义的行为,并且您的程序可能不会执行您期望的操作。(请参阅:)您知道您从未退出主线程中的循环吗?@r3musn0x我知道我从未退出主线程,问题是我想在线程中停止循环。@IvanBotero,从您提供的输出来看,似乎是主线程继续打印,而次线程可能已经退出。打字错误->
(void*)&timer)
timer已经是指针了。您正在传入指向指针的指针,并将其(
((Timer*)参数)->start();
)用作指针。丢失
&
更好的措辞:指向堆栈上的某个地方,指向
计时器本身,并且已经是一个指针。因为我们知道它的确切位置。还有一个稍微聪明一点的选择:首先不要使用动态分配:
Timer(void*)和timer
timer.stop(),而不是泄漏
计时器
,因为它不是
删除
d。至于原子问题,我是个黑客,所以我可能会使用
volatile sig_atomic_t run
9
 => 90
 => 91
 => 92
 => 93
 => 94
 => 95
 => 96
 => 97
 => 98
 => 99
10
Stopping...
 => 100
 => 101
 => 102
 => 103
 => 104
 => 105
 => 106
 => 107
 => 108
 => 109
11