加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

ruby异常如何导致mutices解锁?

发布时间:2020-12-17 07:08:44 所属栏目:百科 来源:网络整理
导读:最近,我一直在使用 Ruby的线程,并发现了一个略微出乎意料的行为.在关键部分,调用raise会导致互斥锁释放.我可以期待这个同步方法,它的块,但它似乎也发生在单独调用锁和解锁时. 例如,下面的代码输出: $ruby testmutex.rb x syncy sync …我希望在宇宙热死之前
最近,我一直在使用 Ruby的线程,并发现了一个略微出乎意料的行为.在关键部分,调用raise会导致互斥锁释放.我可以期待这个同步方法,它的块,但它似乎也发生在单独调用锁和解锁时.

例如,下面的代码输出:

$ruby testmutex.rb 
x sync
y sync

…我希望在宇宙热死之前阻止你.

m = Mutex.new


x = Thread.new() do
  begin
    m.lock
      puts "x sync"
      sleep 5
      raise "x err"
      sleep 5
    m.unlock 
  rescue 
  end
end


y = Thread.new() do
  sleep 0.5
  m.lock
    puts "y sync"
  m.unlock 
end


x.join
y.join

为什么即使x线程中的m.unlock永远不会执行,y线程也可以运行?

解决方法

请注意,如果从x中删除加注和解锁,则行为是相同的.所以你有一种情况,x线程锁定互斥锁,然后线程结束,互斥锁被解锁.

m = Mutex.new
Thread.new{ m.lock; p m.locked? }.join
#=> true

p m.locked?
#=> false

因此,我们看到情况与提高无关.因为你的加注周围有一个开始/救援块,你只需要提前5秒退出x线程.

据推测,解释器会保留由线程锁定的任何互斥锁的跟踪,并在线程死亡时自动并故意解锁它们. (但我无法通过源代码检查来支持这一点.这只是基于行为的猜测.)

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读