【发布时间】:2011-10-24 22:53:03
【问题描述】:
Data safety and GIL removal 提到,如果您没有安装 Giant Interpreter Lock,则会增加竞争条件的风险。该博客文章给出了以下示例:
# As noted in the blog post, this'll work correctly in MRI Ruby (1.8 or 1.9)
# but may or may not work correctly in Rubinius 2.0 or JRuby
@array, threads = [], []
4.times do
threads << Thread.new { (1..100_000).each {|n| @array << n} }
end
threads.each{|t| t.join }
puts @array.size
使代码线程安全的一种方法是进行函数式编程,并且不让线程内的代码修改不是在线程内创建的对象/变量:
threads = 4.times.map do
Thread.new do
sub_array = []
# Modifying sub_array is fine, because it was created by this thread
(1..100_000).each {|n| sub_array << n}
sub_array
end
end
puts threads.map(&:value).flatten(1).size
# Or (and don't forget nil!)
# array = threads.map(&:value).flatten(1) ; nil
# puts array.size
是否可以指定一个线程不允许修改不“属于”它的对象/变量,如果修改则引发警告或异常?
假设线程代码没有做任何异常病态的事情,比如调用ObjectSpace.each_object。
【问题讨论】:
-
“GIL”的意思是“全局解释器锁”,而不是“巨型解释器锁”,虽然我觉得你的解释更有趣。
-
@tadman:我不能为这个 cromulent 词声称功劳:它目前有 2390 次谷歌点击(相对于“全球解释器锁定”的 117K 谷歌点击)。
-
实际上,我认为 YARV 将其称为 GVL(Giant VM Lock)。 GIL 就是 CPython 所称的。
标签: ruby multithreading thread-safety