рд╕рд┐рдВрдХреНрд░рдирд╛рдЗрдЬрд╝реЗрд╢рди рдкрд░ рдиреЛрдЯреНрд╕ред рдЧрддрд┐рд░реЛрдз


рд╣рдорд╛рд░реЗ рдХрдареЛрд░ рд╕рдордп рдореЗрдВ, рдЬрдм рдкреНрд░реЛрд╕реЗрд╕рд░ рдХреА рд╢рдХреНрддрд┐ рдмрдврд╝рдиреЗ (рдЖрд╡реГрддреНрддрд┐) рдмрдВрдж рд╣реЛ рдЧрдИ рдФрд░ рдЪреМрдбрд╝рд╛рдИ (рдереНрд░реЗрдбреНрд╕ рдХреА рд╕рдВрдЦреНрдпрд╛) рдореЗрдВ рдмрдврд╝рдиреЗ рд▓рдЧреА, рддреЛ рд╕рд┐рдВрдХреНрд░рдирд╛рдЗрдЬрд╝реЗрд╢рди рд╕рдорд╕реНрдпрд╛ рдмрд╣реБрдд рддреАрд╡реНрд░ рд╣реИред рд╡реНрдпрд╡рд╣рд╛рд░ рдореЗрдВ рдЗрд╕ рд╕рдорд╕реНрдпрд╛ рдХрд╛ рд╕рд╛рдордирд╛ рдХрд░рддреЗ рд╣реБрдП, рдореИрдВрдиреЗ рдЦреБрдж рдХреЗ рд▓рд┐рдП рдорд╣рд╕реВрд╕ рдХрд┐рдпрд╛ рдХрд┐ рдпрд╣ рдХрд╛рд░реНрдп рдкрд╣рд▓реА рдирдЬрд╝рд░ рдореЗрдВ рд▓рдЧрдиреЗ рдХреА рддреБрд▓рдирд╛ рдореЗрдВ рдмрд╣реБрдд рдЕрдзрд┐рдХ рдЬрдЯрд┐рд▓ рд╣реИ, рдФрд░ рдпрд╣ рдХрд┐рддрдиреА рдЫреБрдкрддрд╛ рд╣реИред рдЗрд╕ рд╕рдорд╕реНрдпрд╛ рдкрд░ рдХрд╛рдо рдХрд░рдиреЗ рдХреА рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдореЗрдВ, рдореЗрд░реЗ рдкрд╛рд╕ рдХрдИ рджрд┐рд▓рдЪрд╕реНрдк рдкреИрдЯрд░реНрди рдереЗ, рдЬрд┐рдиреНрд╣реЗрдВ рдореИрдВ рд╣рдмреНрд░реЛрд╕реИрдХреНрд╡рд┐рдЯреА рдХрд╛ рдкрд░рд┐рдЪрдп рджреЗрдирд╛ рдЪрд╛рд╣рддрд╛ рд╣реВрдВред


рд╕рдмрд╕реЗ рдХрд╖реНрдЯрдкреНрд░рдж рдореБрджреНрджреЛрдВ рдореЗрдВ рд╕реЗ рдПрдХ рд╣реИ рдЬрд┐рд╕реЗ рдЖрдкрдХреЛ рдкреНрд░реЛрдЧреНрд░рд╛рдорд┐рдВрдЧ рдХрд░рдирд╛ рд╣реИ рдЬрдм рдкреНрд░реЛрдЧреНрд░рд╛рдорд┐рдВрдЧ рдорд▓реНрдЯреАрдереНрд░реЗрдбрд┐рдВрдЧ рдбреЗрдбрд▓реЙрдХ рд╣реИред рд╕рдмрд╕реЗ рдЕрдзрд┐рдХ рдмрд╛рд░, рдРрд╕рд╛ рддрдм рд╣реЛрддрд╛ рд╣реИ рдЬрдм рдХрд┐рд╕реА рдереНрд░реЗрдб рдиреЗ рд╕рдВрд╕рд╛рдзрди A рдХреЛ рдкрд╣рд▓реЗ рд╣реА рдмреНрд▓реЙрдХ рдХрд░ рджрд┐рдпрд╛ рд╣реЛрддрд╛ рд╣реИ, рдЬрд┐рд╕рдХреЗ рдмрд╛рдж рд╡рд╣ B рдХреЛ рдмреНрд▓реЙрдХ рдХрд░рдиреЗ рдХреА рдХреЛрд╢рд┐рд╢ рдХрд░рддрд╛ рд╣реИ, рджреВрд╕рд░реЗ рдереНрд░реЗрдб рдиреЗ рд╕рдВрд╕рд╛рдзрди B рдХреЛ рдмреНрд▓реЙрдХ рдХрд░ рджрд┐рдпрд╛ рд╣реИ, рдЬрд┐рд╕рдХреЗ рдмрд╛рдж рд╡рд╣ рд╕рдВрд╕рд╛рдзрди A рдХреЛ рдмреНрд▓реЙрдХ рдХрд░рдиреЗ рдХрд╛ рдкреНрд░рдпрд╛рд╕ рдХрд░рддрд╛ рд╣реИред рдЗрд╕ рдкреНрд░рдХрд╛рд░ рдХреА рдмрдЧ рдореЗрдВ рд╕рдмрд╕реЗ рджреБрдЦрдж рдмрд╛рдд рдпрд╣ рд╣реИ рдХрд┐, рдПрдХ рдирд┐рдпрдо рдХреЗ рд░реВрдк рдореЗрдВ, рд╕реНрдерд┐рддрд┐ рдмрд╣реБрдд рджреБрд░реНрд▓рдн рд╣реИред , рдФрд░ рдкрд░реАрдХреНрд╖рдг рдХреЗ рджреМрд░рд╛рди рдЗрд╕реЗ рдкрдХрдбрд╝рдирд╛ рд▓рдЧрднрдЧ рдЕрд╕рдВрднрд╡ рд╣реИред рддреЛ, рдЖрдкрдХреЛ рдЗрд╕ рдмрдЧ рдХреА рд╕рдВрднрд╛рд╡рдирд╛ рдХреЛ рднреА рд░реЛрдХрдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ! рдХреИрд╕реЗ? рдмрд╣реБрдд рд╕рд░рд▓ рд╣реИред рдпрд╣рд╛рдБ рдкреИрдЯрд░реНрди рдЬрд┐рд╕реЗ рдореИрдВрдиреЗ рд╕рд┐рдВрдХреНрд░реЛрдирд╛рдЗрдЬрд╝реЗрд╢рди рдореИрдирдЬрд░ рдХрд╣рд╛ рд╣реИ, рдЕрд░реНрдерд╛рддреНред рд╕рд┐рдВрдХреНрд░рдирд╛рдЗрдЬрд╝реЗрд╢рди рдкреНрд░рдмрдВрдзрдХред рдкреИрдЯрд░реНрди рдРрд╕реЗ рдорд╛рдорд▓реЛрдВ рдХреЗ рд▓рд┐рдП рдЕрднрд┐рдкреНрд░реЗрдд рд╣реИ, рдЬрдм рдкрд░реНрдпрд╛рдкреНрдд рд░реВрдк рд╕реЗ рдмрдбрд╝реА рд╕рдВрдЦреНрдпрд╛ рдореЗрдВ рд╡рд┐рднрд┐рдиреНрди рд╕рдВрд╕рд╛рдзрдиреЛрдВ рдХрд╛ рд╕рд┐рдВрдХреНрд░рдирд╛рдЗрдЬрд╝реЗрд╢рди рдкреНрд░рджрд╛рди рдХрд░рдирд╛ рдЖрд╡рд╢реНрдпрдХ рд╣реЛред

рд╢реБрд░реВ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП, рд╕рднреА рд╕рдВрд╕рд╛рдзрдиреЛрдВ рдХреЛ рд╕рд╛рдЭрд╛ рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реЛрддреА рд╣реИ рдЬреЛ рдПрдХ рд╡рд┐рд╢реЗрд╖ рдЖрдзрд╛рд░ рд╡рд░реНрдЧ рд╕реЗ рд╡рд┐рд░рд╛рд╕рдд рдореЗрдВ рдкреНрд░рд╛рдкреНрдд рд╣реЛрдиреЗ рдЪрд╛рд╣рд┐рдПред
class SynchPrim { enum{ NOT_LOCKED=0 }; public: SynchPrim(): lockId_( NOT_LOCKED ){} SynchPrim( const SynchPrim& ): lockId_( NOT_LOCKED ){} SynchPrim operator =( const SynchPrim& ){} private: template< typename T >friend class SynchronizationManager; int getLockId()const{ return lockId_; } int lockId_; }; 


рдЦреИрд░, рдЕрднреА рдХреЗ рд▓рд┐рдП, рд╕рдм рдХреБрдЫ рд╕рд░рд▓ рд╣реИред рд▓реЗрдХрд┐рди рдХреНрдпрд╛ рд╣реЛрдЧрд╛ рдЕрдЧрд░ рд╣рдо рдХрдХреНрд╖рд╛ рдореЗрдВ рдПрдХ рдЕрддрд┐рд░рд┐рдХреНрдд рдкреВрд░реНрд╡рдЬ рдЬреЛрдбрд╝рдирд╛ рдирд╣реАрдВ рдЪрд╛рд╣рддреЗ рд╣реИрдВ рдпрд╛ рдирд╣реАрдВ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ? рдпрд╣ рдареАрдХ рд╣реИ, рдЖрдкрдХреЛ рдЗрд╕рдХреЗ рд▓рд┐рдП рдХреЗрд╡рд▓ рдПрдХ рдЖрд╡рд░рдг рд▓рд┐рдЦрдирд╛ рд╣реЛрдЧрд╛:
 template< typename T > class SynchPrimWrapper : public T, public SynchPrim{}; 

рдФрд░ рдПрдХ рд╡рд╕реНрддреБ рдХреА рдШреЛрд╖рдгрд╛ рдХрд░рддреЗ рд╕рдордп рдЗрд╕рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░реЗрдВ:
 SynchPrimWrapper< Resource1 > resource1; 


рдкреИрдЯрд░реНрди рдХрд╛ рдореБрдЦреНрдп рд╡рд┐рдЪрд╛рд░ рдпрд╣ рд╣реИ рдХрд┐ рдЗрд╕ рд╕рдордп рдЖрд╡рд╢реНрдпрдХ рд╕рднреА рд╕рд╛рдЭрд╛ рд╕рдВрд╕рд╛рдзрдиреЛрдВ рдХреЛ рдПрдХ рд╕рд╛рде рдЕрд╡рд░реБрджреНрдз рдХрд┐рдпрд╛ рдЬрд╛рдирд╛ рдЪрд╛рд╣рд┐рдП, рдПрдХ рд╕рд╛рде рдЬрд╛рд░реА рдХрд┐рдпрд╛ рдЬрд╛рдирд╛ рдЪрд╛рд╣рд┐рдП, рдлрд┐рд░ рдЧрддрд┐рд░реЛрдз рдирд╣реАрдВ рд╣реЛ рд╕рдХрддрд╛ рд╣реИред рдпрджрд┐ рд╣рдо рдкрд┐рдЫрд▓реЗ рд╡рд╛рд▓реЗ рдХреЛ рдореБрдХреНрдд рдХрд┐рдП рдмрд┐рдирд╛ рдирдП рд╕рдВрд╕рд╛рдзрдиреЛрдВ рдХреЛ рдЕрд╡рд░реБрджреНрдз рдХрд░рдиреЗ рдХреА рдХреЛрд╢рд┐рд╢ рдХрд░рддреЗ рд╣реИрдВ, рддреЛ рдПрд╕реНрдЯрд░ рдореИрдХреНрд░реЛ рдХрд╛рдо рдХрд░реЗрдЧрд╛ред

рд╕рдмрд╕реЗ рдкрд╣рд▓реЗ, рд╣рдо рд╕рдВрд╕рд╛рдзрдиреЛрдВ рдХреА рдПрдХ рд╕реВрдЪреА рдмрдирд╛рдПрдВрдЧреЗ рдЬрд┐рд╕рдХреЗ рд╕рд╛рде рд╣рдо рдХрд╛рдо рдХрд░реЗрдВрдЧреЗред рдпрд╣ рдпрд╛ рддреЛ C- рд╕рд░рдгреА рдпрд╛ std :: рд╡реЗрдХреНрдЯрд░ рд╣реЛ рд╕рдХрддрд╛ рд╣реИред
 SynchPrim* lock_list[] = { &resource1, &resource2, &resource3 }; 

рдлрд┐рд░ рдПрдХ рдХреЙрд▓ рдХреЗ рд╕рд╛рде рд╣рдо рдЙрди рд╕рднреА рдХреЛ рдмреНрд▓реЙрдХ рдХрд░рддреЗ рд╣реИрдВ:
 SynchronizationManager::getInstance().lock( lock_list+0, lock_list+3 ); 

рд╡реИрд╕реЗ, рд▓реЙрдХ рдлрд╝рдВрдХреНрд╢рди рдЕрддреБрд▓реНрдпрдХрд╛рд▓рд┐рдХ рд▓реЙрдХрд┐рдВрдЧ рдХрд╛ рд╕рдорд░реНрдерди рдХрд░рддрд╛ рд╣реИред рдпрджрд┐ рдЖрдк рдирд╣реАрдВ рдЪрд╛рд╣рддреЗ рдХрд┐ рдереНрд░реЗрдб рддрдм рддрдХ рдкреНрд░рддреАрдХреНрд╖рд╛ рдХрд░реЗрдВ рдЬрдм рддрдХ рдХрд┐ рдХрдмреНрдЬреЗ рд╡рд╛рд▓реЗ рд╕рдВрд╕рд╛рдзрди рдореБрдХреНрдд рди рд╣реЛ рдЬрд╛рдПрдВ, рддреЛ рдЕрдВрддрд┐рдо рдкреИрд░рд╛рдореАрдЯрд░ рдХреЗ рд░реВрдк рдореЗрдВ рдЧрд▓рдд рдкрд╛рд╕ рдХрд░реЗрдВред
рд╕рдВрд╕рд╛рдзрдиреЛрдВ рдХреА рдЕрдм рдЖрд╡рд╢реНрдпрдХрддрд╛ рдирд╣реАрдВ рд╣реЛрдиреЗ рдХреЗ рдмрд╛рдж, рд╣рдо рдЙрдиреНрд╣реЗрдВ рдХреЙрд▓ рдХрд░рдХреЗ рд░рд┐рд╣рд╛ рдХрд░рддреЗ рд╣реИрдВ:
 SynchronizationManager::getInstance().unlock( lock_list+0, lock_list+3 ); 


рдЦреИрд░, рд╡рд╛рд╕реНрддрд╡ рдореЗрдВ рд╡рд░реНрдЧ:
 template< class TSynchronizator >//      lock, unlock, wait, signal   ThreadType class SynchronizationManager : public Singelton< SynchronizationManager< TSynchronizator > > { public: /*         needWait -    true -   ,       false,    */ template< typename Iterator > bool lock( const Iterator& begin, const Iterator& end, bool needWait= true ); /*          */ template< typename Iterator > void unlock( const Iterator& begin, const Iterator& end ); private: TSynchronizator synh_; #ifdef _DEBUG typedef typename TSynchronizator::ThreadType ThreadId; typedef std::set< ThreadId > LockedThreads; LockedThreads lthread_; #endif }; 


рдПрдХ рддреБрд▓реНрдпрдХрд╛рд▓рди рд░рдгрдиреАрддрд┐ рдХрд┐рд╕реА рднреА рд╕рд╛рдзрди рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдХреЗ рд▓рд┐рдЦреА рдЬрд╛ рд╕рдХрддреА рд╣реИ, рдФрд░ рд▓рдЧрднрдЧ рдХрд┐рд╕реА рднреА рдордВрдЪ рдкрд░ред рдЖрдорддреМрд░ рдкрд░, рдпрд╣ рдореНрдпреВрдЯреЗрдХреНрд╕ рдФрд░ рд╕реНрдерд┐рддрд┐ рд╣реИред

рдХрд╛рд░реНрдпрд╛рдиреНрд╡рдпрди:

 template< class TSynchronizator > template< typename Iterator > bool SynchronizationManager< TSynchronizator >::lock( const Iterator& begin, const Iterator& end, bool needWait ) { synh_.lock(); ThreadId threadId = synh_.getThreadId(); bool isFree = false; #ifdef _DEBUG assert( lthread_.find( threadId ) == lthread_.end() ); #endif while( !( isFree = std::find_if( begin, end, std::mem_fun( &SynchPrim::getLockId ) ) == end ) && needWait ) synh_.wait(); if( isFree ) for( Iterator it = begin; it != end; it++ ) (*it)->lockId_ = threadId; #ifdef _DEBUG if( isFree ) lthread_.insert( threadId ); #endif synh_.unlock(); return isFree; } template< class TSynchronizator > template< typename Iterator > void SynchronizationManager< TSynchronizator >::unlock( const Iterator& begin, const Iterator& end ) { synh_.lock(); #ifdef _DEBUG ThreadId threadId = synh_.getThreadId(); assert( lthread_.find( threadId ) != lthread_.end() ); lthread_.erase( threadId ); #endif for( Iterator it = begin; it != end; it++ ) (*it)->lockId_ = SynchPrim::NOT_LOCKED; synh_.signal(); synh_.unlock(); } 

рд╕реНрд╡рд╛рднрд╛рд╡рд┐рдХ рд░реВрдк рд╕реЗ, рдпрд╣ рджреГрд╖реНрдЯрд┐рдХреЛрдг рдХрдорд┐рдпреЛрдВ рдХреЗ рдмрд┐рдирд╛ рдирд╣реАрдВ рд╣реИред рд╣рдореЗрд╢рд╛ рдЕрдЧреНрд░рд┐рдо рдореЗрдВ рдпрд╣ рдЬрд╛рдирдирд╛ рд╕рдВрднрд╡ рдирд╣реАрдВ рд╣реИ рдХрд┐ рд╣рдореЗрдВ рдХрд┐рди рд╕рдВрд╕рд╛рдзрдиреЛрдВ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИред рдЗрд╕ рд╕реНрдерд┐рддрд┐ рдореЗрдВ, рдЖрдкрдХреЛ рдкрд╣рд▓реЗ рд╕реЗ рдЖрд╡рдВрдЯрд┐рдд рд╕рдВрд╕рд╛рдзрдиреЛрдВ рдХреЛ рдЕрдирдмреНрд▓реЙрдХ рдХрд░рдирд╛ рд╣реЛрдЧрд╛ рдФрд░ рдЙрдиреНрд╣реЗрдВ рдПрдХ рдирдП рдкрд░ рдмреНрд▓реЙрдХ рдХрд░рдирд╛ рд╣реЛрдЧрд╛, рд▓реЗрдХрд┐рди рдпрд╣ рдУрд╡рд░рд╣реЗрдб рд╣реИ, рд╡реЗ рд╕рдВрднрд╛рд╡рд┐рдд рдЧрддрд┐рд░реЛрдз рд╕реЗ рдЫреБрдЯрдХрд╛рд░рд╛ рдкрд╛рдиреЗ рдХреЗ рд▓рд┐рдП рдЗрд╕рдХреЗ рд▓рд╛рдпрдХ рд╣реИрдВ - рдЖрдк рддрдп рдХрд░рддреЗ рд╣реИрдВред рдЗрд╕рдХреЗ рдЕрд▓рд╛рд╡рд╛, рдЕрдкрдиреЗ рд╡рд░реНрддрдорд╛рди рд░реВрдк рдореЗрдВ, рдкреИрдЯрд░реНрди рдЖрдкрдХреЛ рдЕрдирд▓реЙрдХ рдХрд┐рдП рдЧрдП рд╕рдВрд╕рд╛рдзрдиреЛрдВ рддрдХ рдкрд╣реБрдВрдЪ рдХреЛ рдирд┐рдпрдВрддреНрд░рд┐рдд рдХрд░рдиреЗ рдХреА рдЕрдиреБрдорддрд┐ рдирд╣реАрдВ рджреЗрддрд╛ рд╣реИ рдФрд░ рд╕рдВрд╕рд╛рдзрдиреЛрдВ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдиреЗ рдХреЗ рдмрд╛рдж рдЕрдирд▓реЙрдХ рдХрд░рдиреЗ рдХреА рдЧрд╛рд░рдВрдЯреА рдирд╣реАрдВ рджреЗрддрд╛ рд╣реИред рдореИрдВ рдЗрд╕ рдмрд╛рд░реЗ рдореЗрдВ рд▓рд┐рдЦреВрдВрдЧрд╛ рдХрд┐ рдпрд╣ рдЕрдЧрд▓реЗ рд▓реЗрдЦ рдореЗрдВ рдХреИрд╕реЗ рдХрд┐рдпрд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИред

Source: https://habr.com/ru/post/In119438/


All Articles