C++并发多线程--多个线程的数据共享和保护

这篇具有很好参考价值的文章主要介绍了C++并发多线程--多个线程的数据共享和保护。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

目录

1--创建并等待多个线程

2--数据共享

2-1--数据只读

2-2--数据读写

2-3--共享数据保护简单案例


1--创建并等待多个线程

        创建多个线程时,可以使用同一个线程入口函数;

        多个线程的执行顺序与操作系统的调度机制有关,并不和创建线程的先后顺序相同;

        一般会将多个线程对象存放在容器中,方便进行管理;

#include <iostream>
#include <thread>
#include <vector>

// 线程入口函数
void myprint(int i){
    std::cout << "This is thread " << i << std::endl; 
}

int main(int argc, char *argv[]){
    std::vector<std::thread> V;
    // 创建5个线程
    for(int i = 0; i < 5; i++){
        V.push_back(std::thread(myprint, i));
    }

    // 等待5个线程
    for(auto iter = V.begin(); iter != V.end(); iter++){
        iter->join();
    }
    // 继续执行主线程
    std::cout << "This is main thread." << std::endl;
    return 0;
}

2--数据共享

2-1--数据只读

#include <iostream>
#include <thread>
#include <vector>

// 共享只读数据
const std::vector<int> read_data = {1, 2, 3};

// 线程入口函数
void myprint(int i){
    // 只读数据
    std::cout << "thread " << i << " read data: " << read_data[0] << ","
    << read_data[1] << "," << read_data[2] << std::endl;
}

int main(int argc, char *argv[]){
    std::vector<std::thread> V;
    // 创建5个线程
    for(int i = 0; i < 5; i++){
        V.push_back(std::thread(myprint, i));
    }

    // 等待5个线程
    for(auto iter = V.begin(); iter != V.end(); iter++){
        iter->join();
    }
    // 继续执行主线程
    std::cout << "This is main thread." << std::endl;
    return 0;
}

2-2--数据读写

        不同线程对共享数据进行读写时,可能会发生冲突,因此需要进行特殊的处理(例如加锁,线程间需互斥等);

2-3--共享数据保护简单案例

        当两个线程对共享数据进行读写时,会发生冲突,可以通过互斥量(mutex)来对共享数据进行加锁(lock)解锁(unlock)等操作;

        lock() 与 unlock() 必须成对匹配,即调用次数相同;

        必须使用同一个互斥量进行加锁和解锁;

        需要选择正确的临界区进行上锁和解锁,即保护区域需正确;文章来源地址https://www.toymoban.com/news/detail-650408.html

#include <iostream>
#include <thread>
#include <list>
#include <mutex> // 引入互斥

class myClass{
public:
    // 收集数据到消息队列
    void inMsgRecvQueue(){
        for(int i = 0; i < 100; i++){
            // 模拟收集消息
            std::cout << "Running inMsgRecvQueue(), insert one value: " 
                << i << std::endl; 

            // 选择正确的临界区进行加锁和解锁
            my_mutex.lock();
            msgRecvqueue.push_back(i); // 消息队列存储消息
            my_mutex.unlock();
        }
    }
    // 从消息队列取数据
    void outMsgRecvQueue(){
        for(int i = 0; i < 100; i++){
            if(!msgRecvqueue.empty()){
                // 选择正确的临界区并使用同一个互斥量进行加锁和解锁
                my_mutex.lock(); // 加锁
                // 取出数据
                int command = msgRecvqueue.front();
                msgRecvqueue.pop_front(); 

                my_mutex.unlock(); // 解锁
            }
            
            else{
                std::cout << "Running outMsgRecvQueue(), " 
                    "the msgRecvqueue is empty" << std::endl;
            }
        }
    }
private:
    std::list<int> msgRecvqueue; // 消息队列
    std::mutex my_mutex; // 创建互斥量 
};

int main(int argc, char *argv[]){
    myClass sample1;
    // 使用成员函数创建线程
    std::thread myInMsgObj(&myClass::inMsgRecvQueue, &sample1); // 收集数据线程
    std::thread myOutMsgObj(&myClass::outMsgRecvQueue, &sample1); // 取出数据线程
    myInMsgObj.join();
    myOutMsgObj.join();

    return 0;
}

到了这里,关于C++并发多线程--多个线程的数据共享和保护的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 50 C++ 多个线程共享资源问题fix方案二 ----- lock_guard类

    在上一节中,我们使用了mutex的lock函数和unlock函数处理共享资源问题 这一节,我们学习使用 lock_guard来处理 共享资源问题。 是个类模版,这个类模版只能对mutex类型进行构造 例子: lock_guardmutex mylock_guard(mymutex); 优点类似于智能指针, 当我们实例化一个 lock_guard后,不需要un

    2024年01月17日
    浏览(28)
  • 《C++并发编程实战》读书笔记(1):线程管控

    包含头文件 thread 后,通过构建 std::thread 对象启动线程,任何可调用类型都适用于 std::thread 。 启动线程后,需要明确是等待它结束、还是任由它独自运行: 调用成员函数 join() 会先等待线程结束,然后隶属于该线程的任何存储空间都会被清除, std::thread 对象不再关联到已结

    2024年02月10日
    浏览(30)
  • JUC并发编程学习笔记(十)线程池(重点)

    线程池:三大方法、七大参数、四种拒绝策略 池化技术 程序的运行,本质:占用系统的资源!优化资源的使用!- 池化技术(线程池、连接池、对象池......);创建和销毁十分消耗资源 池化技术:事先准备好一些资源,有人要用就拿,拿完用完还给我。 线程池的好处: 1、

    2024年02月06日
    浏览(36)
  • C++多线程学习[四]:多线程的通信和同步、互斥锁、超时锁、共享锁

    初始化 (Init):该线程正在被创建。 就绪 (Ready):该线程在就绪列表中,等待CPU的调度。 运行 (Running):该线程正在运行。 阻塞(Blocked):该线程被阻塞挂起。Blocked状态包括:pend(锁、事件、信号量等阻塞)、suspend(主动pend)、delay(延时阻塞)、pendtime(因为锁、

    2024年01月16日
    浏览(22)
  • JUC并发编程学习笔记(一)认知进程和线程

    进程 一个程序,如QQ.exe,是程序的集合 一个进程往往可以包含多个线程,至少包含一个 java默认有两个线程,GC垃圾回收线程和Main线程 线程:一个进程中的各个功能 java无法真正的开启线程,因为java是运行在虚拟机上的,所以只能通过C++,通过native本地方法调用C++开启线程

    2024年02月06日
    浏览(36)
  • Java并发编程学习笔记(一)线程的入门与创建

    认识 程序由指令和数据组成,简单来说,进程可以视为程序的一个实例 大部分程序可以同时运行多个实例进程,例如记事本、画图、浏览器等 少部分程序只能同时运行一个实例进程,例如QQ音乐、网易云音乐等 一个进程可以分为多个线程,线程为最小调度单位,进程则是作

    2024年02月16日
    浏览(39)
  • C++并发与多线程笔记八:async、future、packaged_task、promise

    本文接上文 C++并发与多线程笔记七:condition_variable、wait、notify_one/all 的内容,主要记录 async、future、packaged_task、promise 概念以及用法。 2.1 基本用法 std::async 是个函数模板,用来启动一个异步任务,启动一个异步任务后,它返回一个 std::future 类模板对象。 上述\\\"启动一个异步

    2023年04月13日
    浏览(38)
  • selenium并发处理多个窗口线程/进程任务

    这里以百度搜索为例,通过不同的浏览器来启动不同的线程。

    2024年01月20日
    浏览(33)
  • C++ 多线程 学习笔记

    线程睡眠很稳定,但无线程睡眠不稳定 线程调用类方法: 有参数时调用方法: 当参数为引用时: detach分离线程,分离线程与主线程同时进行,join会使主线程挂起,执行join进来的进程 detach必须让主线程在还住运行的情况下调用,换句话说就是不能让detach的线程还没结束,主

    2024年02月09日
    浏览(28)
  • 数据共享:安全的共享数据方法,保护您的隐私

    作者:禅与计算机程序设计艺术 随着数据流量越来越多,越来越复杂、越来越高速,各种公司、政府机构、组织等,需要更好地管理和保护自己的个人信息,尤其是在一些敏感数据如银行卡信息、信用卡信息等方面,因此,有必要构建一套准确有效的共享数据的方法,以实现

    2024年02月14日
    浏览(34)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包