美文网首页
c++多线程编程

c++多线程编程

作者: 王王王王王景 | 来源:发表于2019-07-15 09:20 被阅读0次

多线程编程知识

[toc]

1.互斥锁

当有一个链表,这个链表需要两个线程互斥访问时,我们就需要互斥锁。为什么呢?因为当一个线程要去使用这个链表时,首先他得先获得锁,一旦发现锁已经被别的线程占用,则无法获得锁将阻塞等待互斥锁被别人解锁,当然也有办法不阻塞,一旦无法获得锁,则直接返回。

1.1 C++11互斥锁的介绍

方法1:直接操作 mutex,即直接调用 mutex 的 lock / unlock 函数

boost::mutex mutex;
mutex.lock();
mutex.unlock();

方法2:使用 lock_guard 自动加锁、解锁。原理是 RAII,和智能指针类似

方法3:使用 unique_lock 自动加锁、解锁

对比lock_guard和unique_lock

std::unique_lock 与std::lock_guard都能实现自动加锁与解锁功能,但是std::unique_lock要比std::lock_guard更灵活,但是更灵活的代价是占用空间相对更大一点且相对更慢一点。

template <typename T>
class ThreadSafeQueue{
public:
         void Insert(T value);
         void Popup(T &value);
         bool Empety();
 
private:
       mutable std::mutex mut_;
       std::queue<T> que_;
       std::condition_variable cond_;
};

template <typename T>
void ThreadSafeQueue::Insert(T value){
    std::lock_guard<std::mutex> lk(mut_);
    que_.push_back(value);
    cond_.notify_one();
}
 
 
template <typename T>
void ThreadSafeQueue::Popup(T &value){
    std::unique_lock<std::mutex> lk(mut_);
//lambda表达式,是一种匿名函数。方括号内表示捕获变量。
//当lambda表达式返回true时(即queue不为空),wait函数会锁定mutex。
//当lambda表达式返回false时,wait函数会解锁mutex同时会将当前线程置于阻塞或等待状态。
    cond_.wait(lk, [this]{return !que_.empety();});
    value = que_.front();
    que_.pop();
}
 
 
template <typename T>
bool ThreadSafeQueue::Empty() const{
        std::lock_guard<std::mutex> lk(mut_);
        return que_.empty();
}

如果只是为了保证数据同步,那么lock_guard完全够用;
如果除了同步,还需要使用condition进行阻塞时,那么就需要用unique_lock。
std::unique_lock相对std::lock_guard更灵活的地方在于在等待中的线程如果在等待期间需要解锁mutex,并在之后重新将其锁定。而std::lock_guard却不具备这样的功能。
boost还要一个boost::mutex::scoped_lock,这个是boost::unique_lock<boost::mutex>的typedef,在C++11中已经禁用。

2.信号量

信号量讲解参考网站

名称 作用域 上锁时
信号量 进程间或线程间(linux仅线程间) 只要信号量的value大于0,其他线程就可以sem_wait成功,成功后信号量的value减一。若value值不大于0,则sem_wait阻塞,直到sem_post释放后value值加一
互斥锁 线程间 只要被锁住,其他任何线程都不可以访问被保护的资源成功后否则就阻塞

条件变量通过允许线程阻塞和等待另一个线程发送信号的方法弥补了互斥锁的不足,它常和互斥锁一起使用。使用时,条件变量被用来阻塞一个线程,当条件不满足时,线程往往解开相应的互斥锁并等待条件发生变化。一旦其它的某个线程改变了条件变量,它将通知相应的条件变量唤醒一个或多个正被此条件变量阻塞的线程。这些线程将重新锁定互斥锁并重新测试条件是否满足。一般说来,条件变量被用来进行线承间的同步。

相关文章

  • 多线程编程

    参考:C++ 并发编程 线程 windsows多线程 new thread(...) linux 多线程: pth...

  • c++操作系统类编程 - read list

    Concurrency C++ in Action Linux多线程服务端编程:使用muduo C++网络库 现代...

  • 技术学习方法论

    C++: 如何看懂《Linux多线程服务端编程——使用muduoC++网络库》于洋的回答

  • C++并发编程实战介绍附下载

    《C++并发编程实战》是一本基于C++11新标准的并发和多线程编程深度指南。内容包括从std::thread、st...

  • c++多线程编程

    多线程编程知识 [toc] 1.互斥锁 当有一个链表,这个链表需要两个线程互斥访问时,我们就需要互斥锁。为什么呢?...

  • C++ 多线程编程

    在开发C++程序时,一般在吞吐量、并发、实时性上有较高的要求。设计C++程序时,总结起来可以从如下几点提高效率: ...

  • CAS与内存屏障: c/c++的内联汇编(S0)

    c++的CAS与内存屏障: c/c++的内联汇编(S0) 多线程编程中偶尔需要接触一些底层的东西,如CAS,原子操...

  • Linux 中的线程局部存储(1)

    在Linux系统中使用C/C++进行多线程编程时,我们遇到最多的就是对同一变量的多线程读写问题,大多情况下遇到这类...

  • JAVA内存模型---JMM

    JAVA多线程编程是JAVA有别于C/C++的一大特性。最近在学习JAVA并发编程的艺术,遇到了很多问题,但是既然...

  • 多线程编程

    多线程编程之Linux环境下的多线程(一)多线程编程之Linux环境下的多线程(二)多线程编程之Linux环境下的...

网友评论

      本文标题:c++多线程编程

      本文链接:https://www.haomeiwen.com/subject/kkrgkctx.html