我正在尝试学习 ruby 中的线程,我正在执行以下代码:
Thread.abort_on_exception = true
threads = 5.times.map do |i|
Thread.new(i) do |j|
raise "Boom!" if j == 1
print "#{j}n"
end
end
i=0
loop do
i+=1
puts "Waiting!!" if i == 10000
break if i == 10**4
end
threads.each do |th|
begin
th.join
rescue RuntimeError => e
puts e
end
end
puts "Done!!"
有时它无一例外地完美运行并显示如下输出:
Waiting!!
0
2
3
4
Boom!
Boom!
Done!!
有时它会异常退出并显示如下输出:
0
2
3
4
threading.rb:5:in `block (2 levels) in <main>': Boom! (RuntimeError)
现在我的问题是:
- 为什么?它退出与运行时错误,而我已经拯救了它。
- 怎么会有两个Boom!在输出。
开发环境:
- 视窗 7 (x64)
- 红宝石 2.1.5
异常发生在线程中,在主线程通过Thread#join
调用到达块之前;具体来说,在你的循环中。问题是,除了冒泡到主线程的异常之外,它实际上可能发生在任何代码行上;因此,您还需要将错误处理封装在线程中。也许它可以返回错误值,但在使用此并发模型时,异常从根本上被破坏。
(为了向自己证明这一点,请尝试在文件顶部设置$DEBUG = true
;这将显示异常真正发生的位置。