C++ 中的互斥量和 lambda 函数

Mutexes and lambda functions in c++

在处理并发问题时我经常使用std::unique_lock<std::mutex>std::lock_guard<std::mutex>,都没有问题。

我还扩展了 std::mutex 以便能够按如下方式使用它:

mutex.protect([](){
    // my protected code here
}) ;

它锁定互斥量并在 lambda 调用前后释放它。

是否已经在 boost 或标准库中实现了类似的行为?

如果您只想在函数内保护代码较小范围,则不需要通过编写自己的保护功能。你可以像下面那样做,使用大括号创建一个本地范围,当范围退出时,互斥量将以异常安全的方式自动解锁。

double process_func() { 
// do some stuff
    { //start a new scope block
      std::lock_guard<my_mutex> g; // mutex is locked here.
      []() { } // your lambda that needs to be protected
    } // Mutex is released here.
// do more stuff
} 

当然这与您的自定义函数相比有缺点, 很难维护。稍后有人可以在不知道他们在做什么的情况下注入更多代码。

Boost 线程有这个:http://www.boost.org/doc/libs/1_58_0/doc/html/thread/synchronization.html#thread.synchronization.with_lock_guard

您可以像预期的那样使用它:

std::mutex mx;

boost::with_lock_guard(mx, []{
    // protected stuff
});

它甚至支持通常的 INVOKE 语义:

int foo(int,double) { return 42; }

// ...

int answer = boost::with_lock_guard(mx, foo, 3, 3.14);

仅手动标准库实现

您可以自己轻松添加这样的内容:

template <typename M, typename F, typename... Args> 
    auto my_with_lock_guard(M& mx, F&& f, Args&&... args) {
        std::lock_guard<M> lk(mx);
        return std::forward<F>(f)(std::forward<Args>(args)...);
    }

如果标准曾经采用这样的提案,您可以轻松地将其换掉。