当前位置: 首页 > news >正文

3. 线程间共享数据

 1. 线程共享数据会造成什么问题?

1.1 读写不一致

多线程读不会造成数据变动,所以没有问题。只要有一个线程设计修改数据,就会导致数据共享出现问题,简单的是数据不一致,严重的是程序访问已经释放的内存,造成程序崩溃。

1.2 顺序不一致(竞态条件)

1.2.1 为什么要有顺序性问题?

因为,读写操作的不同,不同的访问顺序是是十分重要的。

1.2.2  造成顺序性问题的原因?

因为,需要改动多处数据,造成必须要保证改动多出数据时每一步的连续(一个线程多处改动,多次改动,都必须抢占cpu,不能允许其他线程在这个过程被其他线程修改)

1.2.3 如何防止恶性的条件竞争?

什么是恶性竞争?可以理解为破坏程序,导致程序崩溃的,读写不一致程序还能运行,如果释放指针,访问已经释放的地址导致内存崩溃。

防止恶性竞争的方式有:

  1. 修改数据时,每一步动作不被其他线程抢占。(常见的有:互斥锁)
  2. 使用事务,也就是原子操作。(mysql的事务,redis中lua脚本)

2. 互斥方式保护共享数据

2.1 互斥锁

通过std::mutex,然后调用lock和unlock函数。但是通过unlock,则需要在每一个访问共享数据的线程上都调用unlock,同时也要注意抛出异常的问题,所以采用了基于RAII机制lock_guard()函数,构造时加锁,析构时释放锁。

缺点:一旦有暴漏的引用或者指针,那么访问加锁后,仍然能够被访问(可以推导出,加锁并不是锁内存,很可能就是锁变量的访问)。就是:你要访问共享变量,你就需要对所有的访问共享变量的环节都互斥锁,进行访问,不然的话如果通过指针或者引用去访问内存时,是无法解决这个问题的。

class some_data
{
    int a;
    std::string b;
public:
    void do_something();
};

class data_wrapper
{
private:
    some_data data;
    std::mutex m;
public:
    template<typename Function>
    void process_data(Function func)  
    {
        std::lock_guard<std::mutex> l(m);
        func(data);   1.受保护的线程安全的函数,如果多线程访问该函数的时候,就一定线程安全,因为使用了互斥锁。
    }
};

some_data* unprotected;

void malicious_function(some_data& protected_data)
{
    unprotected=&protected_data;
}

data_wrapper x;

void foo()
{
    x.process_data(malicious_function);   2.如果你某天添加功能,以引用或者指针的方式向外部调用恭喜那个变量,这个时候就是非线程安全了,因为malicious_function是非线程安全的。
    unprotected->do_something();   以无保护方式访问本应受保护的共享数据
}

http://www.dtcms.com/a/107817.html

相关文章:

  • 跨网文件安全交换系统|国产信创认证+安全高效传输
  • 2025-4-2 蓝桥杯刷题情况(分布式队列)
  • 智能觉醒:四大AI Agent框架重构未来生产力
  • 简单描述一下Unity物理系统的主要性能消耗点
  • 【高项】信息系统项目管理师(十五)高级项目管理【4分】
  • RocketMq 5.0之后延时消息底层是怎么实现的?
  • C++(匿名函数+继承+多态)
  • MySQL GROUP BY 和 HAVING 子句中 ‘Unknown column‘ 错误的深入解析
  • 详细介绍一下C++的按位运算
  • Tinder上线《The Game Game》
  • mapreduce工作原理
  • 论文阅读10——解开碳排放与碳足迹之间的关系:文献回顾和可持续交通框架
  • TCP四次挥手
  • 《K230 从熟悉到...》颜色识别
  • 归并排序延伸-非递归版本
  • 基于yolo11的BGA图像目标检测
  • Ubuntu18.04 编译 Android7.1代码报错
  • 使用numpy读取数据集
  • Ubuntu Wayland启动腾讯会议并实现原生屏幕共享
  • JS—页面渲染:1分钟掌握页面渲染过程
  • C语言实现排序
  • spring-ai-alibaba第六章阿里dashscope集成mcp百度翻译tools
  • Java 大视界 -- Java 大数据在智慧文旅虚拟场景构建与沉浸式体验增强中的技术支撑(168)
  • STM32F103_LL库+寄存器学习笔记14 - CAN发送完成中断
  • 【小兔鲜】day02 Pinia、项目起步、Layout
  • 2023年CIE SCI1区TOP:序列融合麻雀搜索算法ISSA,深度解析+性能实测
  • N元语言模型的时间和空间复杂度计算
  • 【网络协议】三次握手与四次挥手
  • 【区块链 + 可信存证】创世云区块链存证平台 | FISCO BCOS 应用案例
  • Redis 数据结构的底层实现—字符串、哈希表、列表、集合