【问题标题】:C++ pthread, two threads read a global variableC++ pthread,两个线程读取一个全局变量
【发布时间】:2013-10-21 01:42:06
【问题描述】:

如果有两个线程只读取一个全局变量,是否需要使用互斥锁来锁定和解锁全局变量?

【问题讨论】:

    标签: c++ pthreads mutex


    【解决方案1】:

    如果他们只是在阅读,那么你就不需要锁定。

    【讨论】:

      【解决方案2】:

      如果他们只是在阅读,那么就不需要锁,但如果不是这种情况,那么我认为互斥锁将确保阅读线程在无事可做时不会吃掉资源。

      类似这样的:-

      Thread1() {
      Mutex_lock();
      Process global_variable;
      Unlock_mutex();
      }
      

      Thread2 也是如此

      附带说明:-

      Mutex 一般用于防止多个线程同时访问共享内存或其他资源。还要记住它本身不会锁定任何东西

      【讨论】:

        【解决方案3】:

        如果线程只读取变量并且 没有人 正在写入变量(不是线程之一,也不是其他人),那么没有锁就完全没问题。如果可能发生任何并发修改,那么每个人(包括纯粹的读者)都必须以某种方式同步——通过互斥锁、读/写锁或其他方式。

        【讨论】:

          【解决方案4】:

          一般来说,需要独占访问以防止看到不一致的状态。对于阅读器线程,这意味着避免部分读取

          这是什么意思?想象一下,您有一个存储在两个(原子)整数上的值,例如坐标。

          int i = 3;
          int j = 4;
          

          现在,我们将在 ij 进行修改时读取它们,更准确地说,当 Writer 线程想要以对角线方式从 (3, 4) 移动到 (4, 5) 时:

          Reader     Writer
            |          |
            |        i = 4
            |          |
          i = 4     <pause>
          j = 4        |
            |        j = 5
            |          |
          

          这称为部分读取Reader 线程已经获得了该对象位于(4, 4) 的信息,尽管它从未存在。我让你想想如果用这些坐标来计算飞机的轨迹会发生什么......

          然而,避免部分读取相当容易:应该以原子方式查看突变。

          • 如果没有突变(在读取期间),那么您可以读取
          • 如果有突变,则需要互斥机制(例如读写器互斥锁)

          因此,要回答您的问题,如果唯一的访问是读取访问,则不需要同步。但是如果你有时(甚至不经常)修改读取的信息,那么你需要一些机制。

          【讨论】:

          • 与上述问题类似。例如,我有两个线程。每个线程调用一个对象的方法来获取它的属性,例如 A->getName()。在这种情况下,是否需要互斥锁?
          • @JohnSimpson:一个方法只不过是一个以*this为第一个参数的友元函数的语法糖,所以问题只是关于这个函数做了什么?如果该方法仅以只读方法访问对象,则可以,因此,如果该方法为const 或该函数通过const-pointer 或const-reference 获取对象,则应该可以(注意@987654332 @ 属性在设计时未考虑多线程安全)