鎖類 stdtry 的策略是鎖定 stdadopt 鎖定 stddefer 鎖

建立 std::unique_lock 時,有三種不同的鎖定策略可供選擇:std::try_to_lockstd::defer_lockstd::adopt_lock

  1. std::try_to_lock 允許在不阻塞的情況下嘗試鎖定:
{
    std::atomic_int temp {0};
    std::mutex _mutex;
    
    std::thread t( [&](){
        
        while( temp!= -1){
            std::this_thread::sleep_for(std::chrono::seconds(5));
            std::unique_lock<std::mutex> lock( _mutex, std::try_to_lock);
            
            if(lock.owns_lock()){
                //do something
                temp=0;
            }
        }
    });
    
    while ( true )
    {
        std::this_thread::sleep_for(std::chrono::seconds(1));
        std::unique_lock<std::mutex> lock( _mutex, std::try_to_lock);
        if(lock.owns_lock()){
            if (temp < INT_MAX){
                ++temp;
            }
            std::cout << temp << std::endl;
        }
    }
}
  1. std::defer_lock 允許在不獲取鎖的情況下建立鎖結構。當鎖定多個互斥鎖時,如果兩個函式呼叫者同時嘗試獲取鎖,則會有一個死鎖機會視窗:
{
    std::unique_lock<std::mutex> lock1(_mutex1, std::defer_lock);
    std::unique_lock<std::mutex> lock2(_mutex2, std::defer_lock);
    lock1.lock()
    lock2.lock(); // deadlock here
    std::cout << "Locked! << std::endl;
    //...
}

使用以下程式碼,無論函式中發生什麼,都會以適當的順序獲取和釋放鎖:

   {
       std::unique_lock<std::mutex> lock1(_mutex1, std::defer_lock);
       std::unique_lock<std::mutex> lock2(_mutex2, std::defer_lock);
       std::lock(lock1,lock2); // no deadlock possible
       std::cout << "Locked! << std::endl;
       //...
       
   }
  1. 如果呼叫執行緒當前擁有鎖,則 std::adopt_lock 不會嘗試第二次鎖定。
{
    std::unique_lock<std::mutex> lock1(_mutex1, std::adopt_lock);
    std::unique_lock<std::mutex> lock2(_mutex2, std::adopt_lock);
    std::cout << "Locked! << std::endl;
    //...
}

要記住的是 std::adopt_lock 不能代替遞迴互斥鎖用法。當鎖超出範圍時,互斥鎖被釋放