共享数据的保护 利用const

      常对象:它的数据成员在整个的对象的生存期内不能改变。常对象必须进行初始化,而且不能被被新。

声明 常对象的语法形式为:

const 类型说明符 对象名;

用const 修饰的类成员

    1.常成员函数

类型说明符 函数名(参数表)const;

void print();

void print() const;

以上两个是对print()函数的重载。

注:

(1)const 是函数类型的一个组成部分,因此在函数定义部分也要带const关键字

(2)常对象只能调用常成员函数

(3)常成员函数不能改变目的对象的数据成员的值

#include<iostream>

using namespace std;

class A{

int i;

public:

A(int x):i(x){}

void print() const;

};


void A::print() const {

i+=1;       //删去此语句,程序将能运行成功

cout<<"i="<<i<<endl;

}

int main()

{

A a(2);

a.print();            //在调用常成员函数时,暂时将此对象视为常对象!!! a对象调用的

return 0;

}

以上程序运行错误,错误为在为常成员函数定义时,改变了对象a的数据成员i的值


2.常数据        比较 const int i;static const int q; static int w ;

const int i;需要通过初始化列表来获得初值,此值直到程序结束之前,不能对它进行更新


static  int w;可以直接赋值 利用  类型说明符  类名::w=? 来赋值,可以对它进行更新,但不会产生副本


static const int q;可以直接利用    const int  类名::q=?来赋值,不可以对它进行更新,也不会产生副本


 3.常引用  形参变为常引用 ,引用的对象的数据不能被更新

例子:

class A

func(const A & a)  a中的数据成员不能改变,不能调用此函数的非const成员函数

### C++ 中线程安全的共享数据保护机制 在多线程环境中,当多个线程同时访问同一个共享资源时,可能会引发竞争条件或其他并发问题。为了避免这些问题并确保线程安全性,在 C++ 中可以采用多种方法来保护共享数据。 #### 使用互斥锁(Mutex) 最常见的一种方式是通过 `std::mutex` 来实现对共享数据的独占访问控制。只有获得锁的线程才能访问被保护数据区域,而其他试图获取锁的线程会被阻塞直到当前持有锁的线程释放它[^1]。 ```cpp #include <iostream> #include <thread> #include <vector> #include <mutex> std::mutex mtx; // 定义全局互斥量 int shared_data = 0; void increment() { std::lock_guard<std::mutex> lock(mtx); // 自动管理锁生命周期 ++shared_data; } int main() { const int num_threads = 10; std::vector<std::thread> threads; for(int i=0;i<num_threads;++i){ threads.emplace_back(increment); } for(auto& th : threads){ th.join(); } std::cout << "Final value of shared data is: " << shared_data << "\n"; } ``` 此代码片段展示了如何利用 `std::mutex` 和 RAII 风格的 `std::lock_guard` 来自动管理锁的获取与释放,从而保障了对变量 `shared_data` 的修改操作不会受到竞态影响[^2]。 #### 利用原子类型(Atomic Types) 对于某些简单的数据结构来说,比如整数计数器或者布尔标志位等场景下,可以直接使用标准库提供的原子类如 `std::atomic<int>` 或者模板形式 `std::atomic<T>` 而无需显式定义额外同步原语即可完成基本级别的线程安全保障工作[^3]。 ```cpp #include <iostream> #include <thread> #include <vector> #include <atomic> std::atomic<int> atomic_shared(0); void thread_task(){ for(int i=0;i<1000;i++) atomic_shared++; } int main(){ constexpr size_t NUM_THREADS = 10; std::vector<std::thread> workers(NUM_THREADS, thread_task); for(auto &t :workers)t.join(); std::cout<<"Value after all increments:"<<atomic_shared<<"\n"; return 0; } ``` 上述例子中演示了一个基于原子类型的解决方案,其中每个子任务独立执行一千次自增运算动作,并最终汇总得到预期结果值[^4]. #### 运用读写锁(Reader-Writer Locks) 除了普通的互斥外,还可以考虑引入更细粒度区分对待只读型请求以及改写性质的需求情况下的优化策略——即读者优先模式下的读写锁方案(`std::shared_mutex`) 。这样做的好处在于允许多个消费者同时查看公共资源而不互相干扰的前提下减少等待时间开销[^5]。 ```cpp #include <fstream> #include <string> #include <memory> #include <mutex> #include <shared_mutex> class FileHandler{ private: std::ifstream file_; mutable std::shared_mutex rw_mtx_; public: explicit FileHandler(const char* filename):file_(filename){}; bool read_line(std::string& line)const{ std::shared_lock lk(rw_mtx_); if(file_ && getline(file_,line)){ return true; }else{return false;} }; void reset_position()const{ std::unique_lock ulk(rw_mtx_); file_.clear(); file_.seekg(0,std::ios::beg); }; }; ``` 在这个文件处理器的设计里头,采用了可变成员变量配合上读写锁技术实现了既满足频繁查询又兼顾偶尔重置位置的功能需求平衡点. ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值