windows 临界区

Posted zhiminzeng

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了windows 临界区相关的知识,希望对你有一定的参考价值。

一、windows临界区使用示例

windows临界区的作用与互斥量类似

区别:
(1)windows临界区需要初始化    InitializeCriticalSection(&m_winSec);
(2)进入临界区相当于lock()     EnterCriticalSection(&m_winSec);  
(3)离开临界区相当于unlock()   LeaveCriticalSection(&m_winSec);
(4)在同一线程中,可以多次进入临界区,但是不能多次对互斥量lock();
     但是进入几次临界区,就应该离开几次临界区,否则,相当于锁没有放开
互斥量多次lock() 程序执行会报错。

使用代码示例:(将互斥量和windows临界区的代码放在一起进行了比较)

#include <windows.h>
#define
__WINDOWSJQ_ class MyClass { // 模拟给一个消息队列发消息和处理消息 public: void WriteMessage() // 模拟发消息,也就是往消息队列中写 { for (int i = 0; i < 10000; ++i) { cout << "插入一个元素:" << i << endl; #ifdef __WINDOWSJQ_ EnterCriticalSection(&m_winSec); // 进入临界区 m_messages.push_back(i); LeaveCriticalSection(&m_winSec); // 离开临界区 #else m_mutex.lock(); // lock() 与 unlock() 要成对使用 m_messages.push_back(i); m_mutex.unlock(); #endif } } // 把需要加锁的代码专门提取出来 bool IsMessagesListEmpty(int& iCount) { #ifdef __WINDOWSJQ_ EnterCriticalSection(&m_winSec); // 进入临界区 if (!m_messages.empty()) { iCount = m_messages.front(); m_messages.pop_front(); LeaveCriticalSection(&m_winSec); // 离开临界区 return true; } LeaveCriticalSection(&m_winSec); // 离开临界区 return false; #else m_mutex.lock(); if (!m_messages.empty()) { iCount = m_messages.front(); m_messages.pop_front(); m_mutex.unlock(); // 每条分支语句都要unlock return true; } m_mutex.unlock(); // 每条分支语句都要unlock return false; #endif } void ReadMessage() // 模拟处理消息队列中的消息,从中读,也删除 { int iCount = 0; for (int i = 0; i < 10000; ++i) { if (IsMessagesListEmpty(i)) { cout << "读取的数据为:" << i << endl; } else { cout << "目前消息队列为空" << i << endl; } } } MyClass() { #ifdef __WINDOWSJQ_ InitializeCriticalSection(&m_winSec); // 用临界区之前需要初始化 #endif } private: list<int> m_messages; // 模拟消息队列 mutex m_mutex; // 创建一个互斥量成员对象 #ifdef __WINDOWSJQ_ CRITICAL_SECTION m_winSec; // windows 中的临界区,非常类似于互斥量 mutex // 临界区一定要被初始化 #endif // __WINDOWSJQ_ }; int main() { MyClass ele; std::thread writeThread(&MyClass::WriteMessage, &ele); // std::thread readThread(&MyClass::ReadMessage, &ele); // readThread.join(); writeThread.join(); cout << "主线程" << endl; system("pause"); return 0; }

二、自动析构技术

// 本类用于自动释放windows下的临界区,作用类似于C++11中的 std::lock_guard
class MyWindowsLock  // RAII类 (resource acquisition is initialization)资源获取即初始化
{                    // 构造函数中初始化一个东西,析构函数中释放一个东西
public:
    MyWindowsLock(CRITICAL_SECTION * pSection)
    {
        m_pSection = pSection;
        EnterCriticalSection(m_pSection);
    }
    ~MyWindowsLock()
    {
        LeaveCriticalSection(m_pSection);
    }

private:
    CRITICAL_SECTION * m_pSection;
};

 

以上是关于windows 临界区的主要内容,如果未能解决你的问题,请参考以下文章

windows 临界区

关于C++临界区CriticalSection的问题。

多线程编程之Windows同步方式

C++11多线程 互斥量与Windows临界区

Windows临界区的用法

同步互斥的实现