一个线程提供数据的最快实现,许多线程消耗数据

时间:2009-10-13 22:53:40

标签: c++ linux multithreading

我有很多数据要传播到许多不同的线程。此数据来自单个线程。消费线程可以安全地同时访问容器。

需要将数据合并到容器中的delta delta(50ms< delta< 1),在此期间消耗线程需要被锁定,但不被阻塞。类似地,当数据生成者想要合并数据时,它应该等到任何读取线程完成(这应该很快),但是没有其他人应该开始读取,因为更新需要尽快发生。

我正在使用linux(特定于平台的解决方案非常精细/预期)并且我关心每一毫秒。我应该使用什么样的锁定机制,或者是否有更好的模型解决这个问题?

3 个答案:

答案 0 :(得分:4)

看起来你需要使用pthread读/写锁。它们允许您限制对一个作者或多个读者的访问。查看pthread_rwlock_init以初始化锁,pthread_rwlock_rdlock获取用于读取数据的锁,使用pthread_rwlock_wrlock获取用于写入数据的锁。

答案 1 :(得分:4)

如果只有一个数据生成器线程且内存不是考虑因素,您可能需要考虑使用合并和交换算法。

其中,编写器线程创建数据结构的副本,而读者继续使用原始文件,合并新的更改,然后在互斥或临界区(或读取器/写入器锁)中执行两个结构的交换。如果您的Unix platform supports interlocked exchange as an atomic operation,您可以执行无锁交换,通过实施来最大化读取吞吐量。

答案 2 :(得分:3)

对于pthread读写锁以及一些线程安全的队列来说,这听起来很好用。生产者线程将项目插入队列。工作池将从队列中提取项目并处理数据。我不确定输出是如何工作的,但你可能也希望在这里使用一个线程安全的队列...如果有意义的话,可能是一个优先级队列来自动合并数据。

锁定队列构造只不过是用于独占锁定的互斥锁,用于数据存储的std::queue,以及用于唤醒正在队列中等待的线程的条件变量。 enqueue方法获取锁,插入队列,释放锁,并发出信号。 dequeue方法获取互斥锁,使用互斥锁作为防护等待条件,并在唤醒时将任何数据出列。这是一个非常标准的生产者 - 消费者风格队列。

在推出自己的解决方案之前,您可能需要查看Boost.MPIBoost.Thread。它们都在底层OS实现上提供了更好的C ++接口。我已经使用了Boost.Thread但它没有提供一个很好的消息传递接口,但它确实改进了pthread。

如果您真的进行多重处理,可能需要认真考虑Boost.MPIApache Qpid。我打算在未来的项目中研究QpidAMPQ,因为它们都提供了很好的基于消息的接口。