C++的std::shared_mutex读写锁怎么使用

发布时间:2022-03-15 16:52:57 作者:iii
来源:亿速云 阅读:669

C++的std::shared_mutex读写锁怎么使用

在多线程编程中,读写锁(Read-Write Lock)是一种常见的同步机制,用于解决多个线程同时读取共享资源而只有一个线程能够写入共享资源的问题。C++11引入了std::shared_mutex,它是一种读写锁的实现,允许多个线程同时读取共享资源,但只允许一个线程进行写入操作。本文将详细介绍std::shared_mutex的使用方法,并通过示例代码展示如何在实际编程中应用它。

1. std::shared_mutex简介

std::shared_mutex是C++11标准库中提供的一种读写锁实现。它允许多个线程同时获取共享锁(读锁),但只允许一个线程获取独占锁(写锁)。这种机制非常适合在读多写少的场景中使用,能够显著提高并发性能。

1.1 共享锁与独占锁

1.2 std::shared_mutex的成员函数

std::shared_mutex提供了以下主要成员函数:

2. std::shared_mutex的基本用法

2.1 独占锁的使用

独占锁用于保护写操作,确保同一时间只有一个线程能够修改共享资源。以下是一个简单的示例,展示了如何使用std::shared_mutex的独占锁:

#include <iostream>
#include <thread>
#include <shared_mutex>
#include <vector>

std::shared_mutex mtx;
int shared_data = 0;

void write_data(int value) {
    std::unique_lock<std::shared_mutex> lock(mtx);
    shared_data = value;
    std::cout << "Write data: " << shared_data << std::endl;
}

int main() {
    std::vector<std::thread> threads;
    for (int i = 0; i < 5; ++i) {
        threads.emplace_back(write_data, i);
    }

    for (auto& t : threads) {
        t.join();
    }

    return 0;
}

在这个示例中,write_data函数使用std::unique_lock来获取独占锁,确保每次只有一个线程能够修改shared_data

2.2 共享锁的使用

共享锁用于保护读操作,允许多个线程同时读取共享资源。以下是一个简单的示例,展示了如何使用std::shared_mutex的共享锁:

#include <iostream>
#include <thread>
#include <shared_mutex>
#include <vector>

std::shared_mutex mtx;
int shared_data = 0;

void read_data() {
    std::shared_lock<std::shared_mutex> lock(mtx);
    std::cout << "Read data: " << shared_data << std::endl;
}

int main() {
    std::vector<std::thread> threads;
    for (int i = 0; i < 5; ++i) {
        threads.emplace_back(read_data);
    }

    for (auto& t : threads) {
        t.join();
    }

    return 0;
}

在这个示例中,read_data函数使用std::shared_lock来获取共享锁,允许多个线程同时读取shared_data

3. std::shared_mutex的高级用法

3.1 读写锁的混合使用

在实际应用中,读操作和写操作可能会同时存在。以下示例展示了如何在同一个程序中使用std::shared_mutex的共享锁和独占锁:

#include <iostream>
#include <thread>
#include <shared_mutex>
#include <vector>

std::shared_mutex mtx;
int shared_data = 0;

void read_data() {
    std::shared_lock<std::shared_mutex> lock(mtx);
    std::cout << "Read data: " << shared_data << std::endl;
}

void write_data(int value) {
    std::unique_lock<std::shared_mutex> lock(mtx);
    shared_data = value;
    std::cout << "Write data: " << shared_data << std::endl;
}

int main() {
    std::vector<std::thread> threads;

    // 创建读线程
    for (int i = 0; i < 5; ++i) {
        threads.emplace_back(read_data);
    }

    // 创建写线程
    for (int i = 0; i < 5; ++i) {
        threads.emplace_back(write_data, i);
    }

    // 等待所有线程完成
    for (auto& t : threads) {
        t.join();
    }

    return 0;
}

在这个示例中,读线程和写线程同时运行,std::shared_mutex确保了读操作和写操作的正确同步。

3.2 尝试获取锁

std::shared_mutex还提供了try_locktry_lock_shared函数,用于尝试获取锁而不阻塞。以下示例展示了如何使用这些函数:

#include <iostream>
#include <thread>
#include <shared_mutex>
#include <vector>

std::shared_mutex mtx;
int shared_data = 0;

void try_write_data(int value) {
    if (mtx.try_lock()) {
        shared_data = value;
        std::cout << "Write data: " << shared_data << std::endl;
        mtx.unlock();
    } else {
        std::cout << "Failed to acquire write lock" << std::endl;
    }
}

void try_read_data() {
    if (mtx.try_lock_shared()) {
        std::cout << "Read data: " << shared_data << std::endl;
        mtx.unlock_shared();
    } else {
        std::cout << "Failed to acquire read lock" << std::endl;
    }
}

int main() {
    std::vector<std::thread> threads;

    // 创建写线程
    for (int i = 0; i < 5; ++i) {
        threads.emplace_back(try_write_data, i);
    }

    // 创建读线程
    for (int i = 0; i < 5; ++i) {
        threads.emplace_back(try_read_data);
    }

    // 等待所有线程完成
    for (auto& t : threads) {
        t.join();
    }

    return 0;
}

在这个示例中,try_write_datatry_read_data函数分别尝试获取独占锁和共享锁,如果获取失败则立即返回。

4. 注意事项

5. 总结

std::shared_mutex是C++11标准库中提供的一种读写锁实现,能够有效地解决多线程编程中的读写同步问题。通过合理使用共享锁和独占锁,可以在读多写少的场景中显著提高并发性能。在实际编程中,需要注意避免死锁,并根据具体场景选择合适的同步机制。

希望本文能够帮助你理解并掌握std::shared_mutex的使用方法,并在实际项目中灵活应用。

推荐阅读:
  1. C++开发PHP7中怎么定义常量
  2. C++中double浮点数出现丢失精度的原因是什么

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

c++

上一篇:docker link容器互联如何实现

下一篇:怎么用Vue3+Vite批量导入模块或资源

相关阅读

您好,登录后才能下订单哦!

密码登录
登录注册
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》