Linux多线程服务器编程-1-线程安全的对象生命期管理
创始人
2024-11-14 17:35:00
0

对象的生与死不能由对象自身拥有的mutex(互斥器)来保护.
如何避免对象析构时可能存在的race condi​t​ion(竞态条件)是C++多线程编程面临的基本问题。
对象的销毁可能出现多种竞态条件(race condi​t​ion):
· 在即将析构一个对象时,从何而知此刻是否有别的线程正在执行该对象的成员函数?
· 在调用某个对象的成员函数之前,如何得知这个对象还活着?它的析构函数会不会碰巧执行到一半?

一个线程安全的class应当满足以下三个条件:
· 多个线程同时访问时,其表现出正确的行为。
· 无论操作系统如何调度这些线程,无论这些线程的执行顺序如何交织(interleaving)。
· 调用端代码无须额外的同步或其他协调动作。

C++标准库里的大多数class都不是线程安全的,包括std::string、std::vector、std::map等,因为这些class通常需要在外部加锁才能供多个线程同时访问。

MutexLock与MutexLockGuard
MutexLock一般是别的class的数据成员。
MutexLockGuard封装临界区的进入和退出,即加锁和解锁。MutexLockGuard一般是个栈上对象,它的作用域刚好等于临界区域.

一个线程安全的Counter示例

// A thread-safe counter class Counter : boost::noncopyable {     public:       Counter() : value_(0) {}       int64_t value() const;       int64_t getAndIncrease();      private:       int64_t value_;       mutable MutexLock mutex_; };  int64_t value() const {     MutexLockGuard lock(mutex_);     return value_; }  int64_t getAndIncrease() {     MutexLockGuard lock(mutex_);     int64_t ret = value_++;     return ret; }

对象的创建很简单
· 不要在构造函数中注册任何回调;
· 也不要在构造函数中把this传给跨线程的对象;
· 即便在构造函数的最后一行也不行。
不要泄露this, 别的线程有可能访问这个半成品对象,这会造成难以预料的后果

 // don't do this class Foo : public Observer {     public:       Foo(Observer* s)       {         s->register_(this);  // error, not thread safe       }        virtual void update(); };  // do this class Foo : public Observer {     public:       Foo();       virtual void update();        void observe(Observer* s)       {         s->register_(this);         } };  Foo* pFoo = new Foo; Observable* s = getSubject(); pFoo->observe(s);  // two phase call, or call s->register_(pFoo);

二段式构造——即构造函数+ini​t​ial​ize()——有时会是好办法,这虽然不符合C++教条,但是多线程下别无选择
即使构造函数的最后一行也不要泄露this,因为Foo有可能是个基类,基类先于派生类构造,执行完Foo:​:Foo()的最后一行代码还会继续执行派生类的构造函数,这时most-derived class的对象还处于构造中,仍然不安全。

相对来说,对象的构造做到线程安全还是比较容易的,毕竟曝光少,回头率为零

相关内容

热门资讯

透视步骤!hhpoker智能辅... 透视步骤!hhpoker智能辅助插件,hhpoker辅助软件是真的么(透视)竟然是真的透视app(哔...
透视指南书!HH平台挂,hhp... 透视指南书!HH平台挂,hhpoker是正规的吗(透视)本来是真的透视器(哔哩哔哩)1)hhpoke...
透视模板!wpk辅助器是真的吗... 透视模板!wpk辅助器是真的吗,wpk透视是真的吗(透视)竟然真的有透视神器(哔哩哔哩)1、透视模板...
透视课程!德普之星辅助器app... 透视课程!德普之星辅助器app,德扑圈透视挂(透视)都是是有脚本挂(哔哩哔哩)1.德普之星辅助器ap...
透视阶段!红龙poker有辅助... 透视阶段!红龙poker有辅助吗,pokemmo手机版脚本(透视)真是存在有脚本技巧(哔哩哔哩)透视...
透视总结!约局吧德州可以透视吗... 透视总结!约局吧德州可以透视吗,hardrock透视工具(透视)原来有脚本app(哔哩哔哩)1、这是...
透视课程!wpk辅助,wpk软... 透视课程!wpk辅助,wpk软件是真的吗(透视)总是真的是有脚本工具(哔哩哔哩)1、每一步都需要思考...
透视指引!aapoker安装包... 透视指引!aapoker安装包怎么使用,aapoker辅助器怎么用(透视)好像存在有透视攻略(哔哩哔...
透视手段!aapoker怎么选... 透视手段!aapoker怎么选牌,aapoker透视脚本(透视)原来真的是有脚本app(哔哩哔哩)a...
透视经验!德普之星透视,德普之... 透视经验!德普之星透视,德普之星透视(透视)竟然是有脚本攻略(哔哩哔哩)1、不需要AI权限,帮助你快...