Namespaces
Variants

std::shared_mutex:: lock

From cppreference.net
Concurrency support library
Threads
(C++11)
(C++20)
this_thread namespace
(C++11)
(C++11)
Cooperative cancellation
Mutual exclusion
Generic lock management
Condition variables
(C++11)
Semaphores
Latches and Barriers
(C++20)
(C++20)
Futures
(C++11)
(C++11)
(C++11)
Safe reclamation
Hazard pointers
Atomic types
(C++11)
(C++20)
Initialization of atomic types
(C++11) (deprecated in C++20)
(C++11) (deprecated in C++20)
Memory ordering
(C++11) (deprecated in C++26)
Free functions for atomic operations
Free functions for atomic flags
void lock ( ) ;
(начиная с C++17)

Получает эксклюзивное владение shared_mutex . Если другой поток удерживает эксклюзивную блокировку или разделяемую блокировку на том же shared_mutex , вызов lock заблокирует выполнение до тех пор, пока все такие блокировки не будут сняты. Пока shared_mutex заблокирован в эксклюзивном режиме, никакие другие блокировки любого типа не могут быть установлены.

Если lock вызывается потоком, который уже владеет shared_mutex в любом режиме (эксклюзивном или разделяемом), поведение не определено. Предыдущая операция unlock() на том же мьютексе синхронизируется-с (как определено в std::memory_order ) этой операцией.

Содержание

Параметры

(нет)

Возвращаемое значение

(нет)

Исключения

Выбрасывает std::system_error при возникновении ошибок, включая ошибки базовой операционной системы, которые могут помешать lock выполнить свои спецификации. Мьютекс не блокируется в случае выбрасывания любого исключения.

Примечания

lock() обычно не вызывается напрямую: std::unique_lock , std::scoped_lock и std::lock_guard используются для управления эксклюзивной блокировкой.

Пример

#include <chrono>
#include <iostream>
#include <mutex>
#include <shared_mutex>
#include <syncstream>
#include <thread>
#include <vector>
std::mutex stream_mutx;
void print(auto const& v)
{
    std::unique_lock<std::mutex> lock(stream_mutx);
    std::cout << std::this_thread::get_id() << " saw: ";
    for (auto e : v)
        std::cout << e << ' ';
    std::cout << '\n';
}
int main()
{
    using namespace std::chrono_literals;
    constexpr int N_READERS = 5;
    constexpr int LAST = -999;
    std::shared_mutex smtx;
    int product = 0;
    auto writer = [&smtx, &product](int start, int end)
    {
        for (int i = start; i < end; ++i)
        {
            auto data = i;
            {
                std::unique_lock<std::shared_mutex> lock(smtx); // better than:
                                                                // smtx.lock();
                product = data;
            }
            std::this_thread::sleep_for(3ms);
        }
        smtx.lock(); // lock manually
        product = LAST;
        smtx.unlock();
    };
    auto reader = [&smtx, &product]
    {
        int data = 0;
        std::vector<int> seen;
        do
        {
            {
                // better to use:
                std::shared_lock lock(smtx); // smtx.lock_shared();
                data = product;
            }                                // smtx.unlock_shared();
            seen.push_back(data);
            std::this_thread::sleep_for(2ms);
        }
        while (data != LAST);
        print(seen);
    };
    std::vector<std::thread> threads;
    threads.emplace_back(writer, 1, 13);
    threads.emplace_back(writer, 42, 52);
    for (int i = 0; i < N_READERS; ++i)
        threads.emplace_back(reader);
    for (auto&& t : threads)
        t.join();
}

Возможный вывод:

127755840 saw: 43 3 3 4 46 5 6 7 7 8 9 51 10 11 11 12 -999
144541248 saw: 2 44 3 4 46 5 6 7 7 8 9 51 10 11 11 12 -999
110970432 saw: 42 2 3 45 4 5 47 6 7 8 8 9 10 11 11 12 -999
119363136 saw: 42 2 3 4 46 5 6 7 7 8 9 9 10 11 11 12 12 -999
136148544 saw: 2 44 3 4 46 5 6 48 7 8 9 51 10 11 11 12 12 -999

Смотрите также

пытается заблокировать мьютекс, возвращает управление если мьютекс недоступен
(public member function)
разблокирует мьютекс
(public member function)
блокирует мьютекс для совместного владения, блокируется если мьютекс недоступен
(public member function)