YARV Arrays的push / pop方法是否是线程安全的?

时间:2018-08-13 19:20:18

标签: ruby yarv

假设我有一对(生产者,消费者)YARV线程(TpTc)共享Array q-Tp推送到{ {1}},然后弹出q。如果执行下推和弹出操作的顺序并不重要,那么代码是否可以在没有任何同步机制的情况下工作?

1 个答案:

答案 0 :(得分:2)

由于其全局解释器锁(GIL),因此在大多数情况下访问数组在MRI / YARV中(并且仅在那儿)是线程安全的,

您仍然必须确保每次仅执行一次操作,并避免读/写结构。在Rubinius或JRuby之类的其他Ruby实现中,数组显然不是线程安全的。

话虽如此,Ruby附带了一个用于线程间通信的不同原语,巧合的是MRI / VARV中唯一一个明确具有线程安全性的类:Queue。它支持以线程安全的方式推送和弹出对象。

从Ruby文档中获取以下示例:

queue = Queue.new

producer = Thread.new do
  5.times do |i|
     sleep rand(i) # simulate expense
     queue << i
     puts "#{i} produced"
  end
end

consumer = Thread.new do
  5.times do |i|
     value = queue.pop
     sleep rand(i/2) # simulate expense
     puts "consumed #{value}"
  end
end

还有一个名为concurrent-ruby的维护良好的项目,该项目为跨线程并发编程提供了许多强大的原语。