zoukankan      html  css  js  c++  java
  • 3.多线程系列文章 之 线程的同步[1/2]

    目录

    2.1 简介

    2.2 Qmutex 应用

    2.3 QWaitCondition 应用

     

    接下来继续说线程同步的问题,当n个线程在一起运行时,为了控制其先后运行顺序,或者 对共享数据的访问 ,这就需要用到线程的功能,这仅是我能想到的两个情形.

     

    QT 提供 QMutex, QReadWriteLock, QSemaphore  QWaitCondition  用以提供线程同步.这里就选用QMutex,QWaitCondition 结合一个 “下载工具” 例子  分别讲解说明,其他的以后需用到再说. 如果一篇文章全部讲完,实在够呛,能力有限

     

     

    2.1 Qmutex 应用

         首先我们将使用 QMutex来实现 下载工具 中的 “下载/暂停/停止”三种下载状态切换,以下简称为状态切换。

           简单说一下Qmutex,该类是用来同步线程最基础的类。一般通过调用lock /unlock方法.使Qmutex就是像检测一个标志一样,如果不是true就继续等待,只不过这个等待的过程不会占用cpu时间片。这和循环检测每个标志位有明显的不同。

        使用QMutext需要注意的两点是:

        1.在同一线程中,Qmutex 不能重复lock或unlock,换句话说就是lock/unlock 只能成对出现。幸好的是如果你不小心这么做的时候,debug时有所提示.

         2.线程lock后,只能在同一个线程中进行unlock,例如,A线程lock后,如果企图在B线程直接unlock 来释放,这将会引发错误。

     

    上回讲到线程的控制提到sleep是无法休眠到一半然后唤醒的. 使用Qmutex  可以改变 sleep完全没有回应的局面。在这里我们需要用一个变量做开关,使用Qmutex  做同步访问以达到一种唤醒的效果,也就是我们要做的状态切换了,只不过说法不同。

     

    想象一下该下载工具,为了ui的响应,一般运行时有两个线程.一个是main线程用于gui,另一个是worker线程,用于下载数据,用户随时决定要进行状态切换.

     

    下面是关键的代码部分

     

    #include <QThread>
    #include <QMutex>
    
    
    
    class CThread : public QThread
    {
    
    public:
        CThread();
        ~CThread();
    public:
        enum E_downloadState{DS_INIT,DS_START, DS_PAUSE, DS_STOP};
        void startDownload();
        void pauseDownload();
        void stopDownload();
        E_downloadState  downState() const;
    
    protect:
        void run();
    
    private:
        QMutex mDownloadMutex;
        E_downloadState  mState; //用于mutex的变量
    
        void setDownloadMutex(bool lock);
        void setDownState( E_downloadState state);
    
    };
    
    

     

    画个示意图

     

    开始下载:

     clip_image002

     

     

    暂停下载

    clip_image004

     

    中止下载

     clip_image006

     

     

     

     

     

    在这里为了看清整个控制过程,我用qDebug()模拟出下载工具的状态切换

    image

  • 相关阅读:
    MyBatis 最常见错误,启动时控制台无限输出日志
    mybatis.generator.configurationFile
    MBG 相关资源链接
    MyBatis Generator 详解 专题
    随笔分类
    android 播放assets文件里视频文件的问题
    AssetManager中的路径参数不能包含"assets/"
    Android---intent传递putStringArrayListExtra
    android中使用setVideoURI()播放视频
    vitamio官方demo源码分析
  • 原文地址:https://www.cnblogs.com/foxhengxing/p/1839607.html
Copyright © 2011-2022 走看看