/*******************************************************************************************/

一、为什么需要使用线程

图形界面中一旦使用了线程休眠,图形界面就不会刷新(不会动),呈现卡住无响应的状态。

这是由于图形界面中是单线程的

所以  很复杂的数据处理 耗时长的,就需要创建线程。

 

QThread 线程类,

qt中的线程睡眠函数:QThread::sleep();

 

void MyWidget::on_pushButton_clicked()

{

    //如果定时器没有工作

    if(myTimer->isActive() == false)

    {

        myTimer->start(100);

    }

 

    //很复杂的数据处理

    //需要耗时5s

    sleep(5);//图形界面中一旦使用了线程休眠,图形界面就不会刷新(不会动),呈现卡住无响应的状态。

                  //也就是说由于睡眠,导致前面启动了的定时器都不工作

                             

         myTimer->stop();//过了5s后图形界面才会有响应。但是

           //此时是停了定时器,前面是睡眠 定时器也不工作,所以呈现出一直定时器一直不工作的状态

}

 

/*******************************************************************************************/

二、线程

1.Qt4.7以前 线程的使用方法:

1).自定义一个类,继承于QThread

class MyThread : public QThread

{

public:

  void run();//只有这个是线程处理函数(和主线程不在同一个线程),虚函数。

}

 

2).使用自定义的类创建对象,并开启线程

MyThread myThread;

 

//启动线程

//注意不能直接调用run函数,否则还是在主线程里面运行,而不是在新线程里面

myThread.start();//间接调用run

 

3).返回处理结果,告诉处理完

可以在类中定义一个信号,然后在需要(处理好后)的时候发送这个信号,来告诉其他线程。

 

具体见图《线程1》

 界面编程之QT的线程20180731

2.实现:

在项目中添加一个继承QThread的类,添加的时候注意由于这个不是控件,所以下拉框选择QObject,然后

再在文件中把基类改为QThread

class MyThread : public QThread

{

    Q_OBJECT

public:

    explicit MyThread(QObject *parent = 0);

 

protected:

    //QThread的虚函数

    //线程处理函数

    //不能直接调用,通过start()间接调用

    void run();

 

signals:

    void isDone();

 

public slots:

};

void MyThread::run()

{

    //很复杂的数据处理

    //需要耗时5s

    sleep(5);

 

    emit isDone();

}

    //分配空间

    thread = new MyThread(this);

 

    //处理线程中的信号,最好用这种传统的方式

    connect(thread, &MyThread::isDone, this, &MyWidget::dealDone);

         //当按窗口右上角x时,窗口触发destroyed(),否则关了窗口线程还会运行

    connect(this, &MyWidget::destroyed, this, &MyWidget::stopThread);

void MyWidget::dealDone()

{

    qDebug() << "it is over";

    myTimer->stop(); //关闭定时器

}

void MyWidget::on_pushButton_clicked()

{

    //如果定时器没有工作

    if(myTimer->isActive() == false)

    {

        myTimer->start(100);

    }

    //启动线程,处理数据

    thread->start();

}

void MyWidget::stopThread()

{

    //停止线程,不是立马关闭,释放线程占用的内存,线程号等资源。和下面配合使用

    thread->quit();//类似linux中,pthread_exit()

    //等待线程处理完手头动作

    thread->wait();//类似linux中,pthread_join , pthread_detach,

        

         //terminate 强制结束,很暴力,往往会导致内存问题。所以一般不用

}

上述代码具体见《QThread》

 1 #ifndef MYWIDGET_H
 2 #define MYWIDGET_H
 3 
 4 #include <QWidget>
 5 #include <QTimer> //定时器头文件
 6 #include "mythread.h" //线程头文件
 7 
 8 namespace Ui {
 9 class MyWidget;
10 }
11 
12 class MyWidget : public QWidget
13 {
14     Q_OBJECT
15 
16 public:
17     explicit MyWidget(QWidget *parent = 0);
18     ~MyWidget();
19 
20     void dealTimeout(); //定时器槽函数
21     void dealDone(); //线程结束槽函数
22     void stopThread(); //停止线程槽函数
23 
24 private slots:
25     void on_pushButton_clicked();
26 
27 private:
28     Ui::MyWidget *ui;
29 
30     QTimer *myTimer; //声明变量
31     MyThread *thread; //线程对象
32 };
33 
34 #endif // MYWIDGET_H
mywidget.h

相关文章:

  • 2021-12-16
  • 2022-12-23
  • 2021-12-06
  • 2022-12-23
  • 2021-07-20
  • 2021-08-18
  • 2021-12-06
猜你喜欢
  • 2021-12-06
  • 2021-12-06
  • 2021-12-06
  • 2021-12-06
  • 2021-12-06
  • 2021-12-06
  • 2021-12-06
相关资源
相似解决方案