简体   繁体   English

提升Mutex Scoped Lock

[英]Boost Mutex Scoped Lock

I was reading through a Boost Mutex tutorial on drdobbs.com, and found this piece of code: 我正在阅读drdobbs.com上的Boost Mutex教程,并发现了这段代码:

#include <boost/thread/thread.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/bind.hpp>
#include <iostream>

boost::mutex io_mutex;

void count(int id)
{
  for (int i = 0; i < 10; ++i)
  {
    boost::mutex::scoped_lock
      lock(io_mutex);
    std::cout << id << ": " <<
      i << std::endl;
  }
}

int main(int argc, char* argv[])
{
  boost::thread thrd1(
    boost::bind(&count, 1));
  boost::thread thrd2(
    boost::bind(&count, 2));
  thrd1.join();
  thrd2.join();
  return 0;
}

Now I understand the point of a Mutex is to prevent two threads from accessing the same resource at the same time, but I don't see the correlation between io_mutex and std::cout. 现在我明白Mutex的意思是阻止两个线程同时访问同一个资源,但我没有看到io_mutex和std :: cout之间的相关性。 Does this code just lock everything within the scope until the scope is finished? 这个代码是否只是锁定范围内的所有内容,直到范围完成为止?

Now I understand the point of a Mutex is to prevent two threads from accessing the same resource at the same time, but I don't see the correlation between io_mutex and std::cout. 现在我明白Mutex的意思是阻止两个线程同时访问同一个资源,但我没有看到io_mutex和std :: cout之间的相关性。

std::cout is a global object , so you can see that as a shared resource. std::cout是一个全局对象 ,因此您可以将其视为共享资源。 If you access it concurrently from several threads, those accesses must be synchronized somehow, to avoid data races and undefined behavior. 如果从多个线程同时访问它,则必须以某种方式同步这些访问,以避免数据争用和未定义的行为。

Perhaps it will be easier for you to notice that concurrent access occurs by considering that: 通过考虑以下情况,您可能会更容易注意到并发访问:

std::cout << x

Is actually equivalent to: 实际上相当于:

::operator << (std::cout, x)

Which means you are calling a function that operates on the std::cout object, and you are doing so from different threads at the same time. 这意味着您正在调用一个在std::cout对象上运行的函数,并且您正在同时从不同的线程执行此操作。 std::cout must be protected somehow. 必须以某种方式保护std::cout But that's not the only reason why the scoped_lock is there (keep reading). 但这并不是scoped_lock存在的唯一原因(继续阅读)。

Does this code just lock everything within the scope until the scope is finished? 这个代码是否只是锁定范围内的所有内容,直到范围完成为止?

Yes, it locks io_mutex until the lock object itself goes out of scope (being a typical RAII wrapper), which happens at the end of each iteration of your for loop. 是的,它会锁定io_mutex直到锁定对象本身超出范围(作为典型的RAII包装器),这发生在for循环的每次迭代结束时。

Why is it needed? 为什么需要它? Well, although in C++11 individual insertions into cout are guaranteed to be thread-safe, subsequent, separate insertions may be interleaved when several threads are outputting something. 好吧,尽管在C ++ 11中,单个插入到cout中的插入保证是线程安全的,但是当几个线程输出某些内容时,后续的单独插入可能会交错。

Keep in mind that each insertion through operator << is a separate function call, as if you were doing: 请记住,每个通过operator <<插入都是一个单独的函数调用,就像你在做的那样:

std::cout << id;
std::cout << ": ";
std::cout << i;
std::cout << endl;

The fact that operator << returns the stream object allows you to chain the above function calls in a single expression (as you have done in your program), but the fact that you are having several separate function calls still holds. operator <<返回流对象的事实允许您在单个表达式中链接上述函数调用(就像您在程序中所做的那样),但是您仍然拥有几个单独的函数调用这一事实。

Now looking at the above snippet, it is more evident that the purpose of this scoped lock is to make sure that each message of the form: 现在看一下上面的代码片段,更明显的是这个范围锁的目的是确保表单中的每条消息:

<id> ": " <index> <endl>

Gets printed without its parts being interleaved with parts from other messages. 获取打印时不将其部分与其他消息中的部分交错。

Also, in C++03 (where insertions into cout are not guaranteed to be thread-safe) , the lock will protect the cout object itself from being accessed concurrently. 此外,在C ++ 03中(其中插入到cout并不保证是线程安全的),锁将保护cout对象本身不被同时访问。

A mutex has nothing to do with anything else in the program (except a conditional variable), at least at a higher level. 互斥锁与程序中的任何其他内容(条件变量除外)无关,至少在更高级别。 A mutex has two effeccts: it controls program flow, and prevents multiple threads from executing the same block of code simultaneously. 互斥锁有两个有效之处:它控制程序流,并防止多个线程同时执行相同的代码块。 It also ensures memory synchronization. 它还确保了内存同步。 The important issue here, is that mutexes aren't associated with resources, and don't prevent two threads from accessing the same resource at the same time. 这里的重要问题是互斥体与资源无关,并且不会阻止两个线程同时访问同一资源。 A mutex defines a critical section of code, which can only be entered by one thread at a time. 互斥锁定义代码的关键部分,一次只能由一个线程输入。 If all of the use of a particular resource is done in critical sections controled by the same mutex, then the resource is effectively protected by the mutex. 如果在由相同互斥锁控制的关键部分中完成对特定资源的所有使用,则该资源将受到互斥锁的有效保护。 But the relationship is established by the coder, by ensuring that all use does take place in the critical sections. 但是这种关系是由编码人员确定的,确保所有使用确实发生在关键部分。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM