In C++, std::mutex, std::lock_guard, std::unique_lock, and std::shared_lock are synchronization primitives used to manage access to shared resources in multithreaded programming. Here's a detailed comparison:
1. std::mutex
- What it is: A basic locking primitive.
- Usage: Used to protect shared data from being simultaneously accessed by multiple threads.
- Pros:
- Explicit control over locking and unlocking.
- Lightweight and straightforward.
- Cons:
- Manual locking/unlocking can lead to mistakes like forgetting to unlock (risking deadlocks).
Example:
std::mutex mtx;
void threadSafeFunction() {
mtx.lock();
// Critical section
mtx.unlock();
}
2. std::lock_guard
- What it is: A RAII (Resource Acquisition Is Initialization) wrapper for
std::mutex. - Usage: Automatically locks the mutex on creation and unlocks it when it goes out of scope.
- Pros:
- Reduces risk of forgetting to unlock.
- Simplifies code by managing the mutex lifecycle automatically.
- Cons:
- Less flexible than
std::unique_lock.
- Less flexible than
Example:
std::mutex mtx;
void threadSafeFunction() {
std::lock_guard<std::mutex> lock(mtx);
// Critical section
// Automatically unlocks when `lock` goes out of scope
}
3. std::unique_lock
- What it is: A more flexible RAII wrapper for
std::mutex. - Usage: Provides advanced features like deferred locking, timed locking, and ability to transfer ownership.
- Pros:
- Flexibility in lock acquisition and release.
- Supports features like
try_lockanddefer_lock.
- Cons:
- Slightly heavier than
std::lock_guarddue to its flexibility.
- Slightly heavier than
Example:
std::mutex mtx;
void threadSafeFunction() {
std::unique_lock<std::mutex> lock(mtx);
// Critical section
lock.unlock(); // Manual unlocking if needed
// Can also relock later
lock.lock();
}
4. std::shared_lock
- What it is: A lock for
std::shared_mutexthat allows multiple threads to acquire shared (read-only) access. - Usage: Use with
std::shared_mutexwhen you need shared (read) and exclusive (write) locking. - Pros:
- Optimized for scenarios where multiple threads read and fewer write.
- Cons:
- Requires
std::shared_mutex, which is slightly heavier thanstd::mutex.
- Requires
Example:
#include <shared_mutex>
std::shared_mutex sharedMtx;
void reader() {
std::shared_lock<std::shared_mutex> lock(sharedMtx);
// Shared access (read-only)
}
void writer() {
std::unique_lock<std::shared_mutex> lock(sharedMtx);
// Exclusive access (write)
}
When to Use What
| Use Case | Recommended Lock |
|---|---|
| Basic locking/unlocking | std::mutex |
| Simple RAII-based lock | std::lock_guard |
| Need flexibility (e.g., timed lock) | std::unique_lock |
| Read-write access (multiple readers) | std::shared_lock (with std::shared_mutex) |
Summary:
- Use
std::mutexfor explicit control over locking. - Prefer
std::lock_guardfor simplicity and safety in most cases. - Use
std::unique_lockfor advanced locking scenarios. - Use
std::shared_lockwhen you need shared read and exclusive write access.
No comments:
Post a Comment