【问题标题】:Multiple threads operating on std::vector: do I need a lock in this case?在 std::vector 上运行的多个线程:在这种情况下我需要锁吗?
【发布时间】:2013-10-05 11:40:34
【问题描述】:

我有一个“侦听器”线程,它查看std::vector“接收者”,将其放入大小为receivers.size() 的数组中,并在其上执行MPI_Waitany,它将返回数组中的索引完成接收操作的元素。

完成的元素然后通过以下方式从接收者向量中删除:

receivers.erase(receivers.begin() + completed_index);

但是,其他线程可以在此过程中将元素推送到“接收者”向量,通过:

receivers.push_back(receiver_message);

这很危险吗?我知道如果添加的元素导致 C++ 调整向量的大小,迭代器可能会变得无效,但是由于我擦除中的迭代器发生在一个点然后被丢弃,这不是我的目的的原子操作吗?

如果需要锁定,我是否需要在每次想要访问向量的任何元素时锁定向量?例如

MPI_Start(&(receivers.at(0)->request));

即使元素 0 从不改变也需要锁? ('request' 只是元素的一个成员)

谢谢

【问题讨论】:

标签: c++ multithreading vector mpi


【解决方案1】:

简单的规则是,如果任何线程要写入向量(大致翻译为“以任何方式修改它”),那么您需要为所有线程使用锁以实现一致的视图。

当且仅当向量是严格只读的,你可以不用锁。

【讨论】:

    【解决方案2】:

    在内部,STL 中的向量被实现为该向量类型的连续内存块。当您修改向量时,它可能会调整内存块的大小并将现有值复制到新位置,然后再删除旧内存。多个并发访问器可能会在旧位置更改此内部存储器,因此必须锁定。最重要的是,vector 保留了当前分配大小和当前使用情况的内部计数,这些计数无论如何都不同步。您可以在不同步的情况下销毁内部簿记。

    【讨论】:

      猜你喜欢
      • 2015-10-11
      • 1970-01-01
      • 1970-01-01
      • 2014-04-12
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-07-01
      相关资源
      最近更新 更多