面试题答案
一键面试常见锁机制原理及适用场景
- 互斥锁(Mutex)
- 原理:互斥锁是一种二元信号量,它只有两种状态:锁定(locked)和解锁(unlocked)。线程在访问共享资源前需要先获取互斥锁,将其状态设为锁定,访问结束后释放互斥锁,将其状态设为解锁。同一时间只有一个线程能获取到互斥锁,从而保证共享资源的线程安全。
- 适用场景:适用于对共享资源的读写操作都需要保证线程安全的场景,无论读操作还是写操作都需要先获取互斥锁,防止多个线程同时访问共享资源造成数据不一致。
- 读写锁(Read - Write Lock)
- 原理:读写锁区分了读操作和写操作。允许多个线程同时进行读操作,因为读操作不会修改共享资源,不会造成数据不一致。但是写操作时,必须独占资源,防止其他线程读或写。当有线程在写时,其他线程无论是读还是写都需要等待。
- 适用场景:适用于读操作远多于写操作的场景。读操作可以并发执行,提高系统性能,而写操作时保证数据一致性。
使用 std::mutex
和 std::lock_guard
保护共享资源示例
#include <iostream>
#include <vector>
#include <mutex>
std::mutex mtx;
std::vector<int> networkData;
void addData(int num) {
std::lock_guard<std::mutex> lock(mtx);
networkData.push_back(num);
}
void printData() {
std::lock_guard<std::mutex> lock(mtx);
for (int num : networkData) {
std::cout << num << " ";
}
std::cout << std::endl;
}
在上述代码中,std::mutex mtx
定义了一个互斥锁。addData
函数和 printData
函数在访问 networkData
这个共享资源前,都通过 std::lock_guard<std::mutex> lock(mtx)
创建了一个 lock_guard
对象,它在构造时自动获取互斥锁,在析构时自动释放互斥锁,从而保证了 networkData
操作的线程安全性。