关于锁的一些问题

糯米粽子1218 2019-07-18 04:12:04
前几天面试时,被问到一个问题:

比如A方法中要使用某个资源,要先给这个资源加个锁,加锁后的处理代码中,如果调用了B方法,而且B方法也需要使用这个资源,这时候怎么处理呢?

逻辑就是以下这样的

lock(data)
{
B();
}

public void B()
{
//此处会读写data
}

因为对锁不是太了解,最后没有给出解决方案,之后查了也没查到改如何实现

特来请教各位大神
...全文
673 20 打赏 收藏 转发到动态 举报
写回复
用AI写文章
20 条回复
切换为时间正序
请发表友善的回复…
发表回复
恒_星 2019-07-25
  • 打赏
  • 举报
回复
重入锁就可以了
xiaoxiangqing 2019-07-24
  • 打赏
  • 举报
回复
不能互相锁,不然就是死锁了
weixin_44564435 2019-07-24
  • 打赏
  • 举报
回复
学习了,哈哈哈
左耳边的期盼 2019-07-23
  • 打赏
  • 举报
回复
学习了。。。
糯米粽子1218 2019-07-23
  • 打赏
  • 举报
回复
引用 15 楼 戴明智 的回复:
用可重入锁应该就可以了,a方法获取锁后,在方法内部的b方法不用再获取锁
是你说的这个概念,可重入锁,我去查了下实现 https://www.cnblogs.com/dj3839/p/6580765.html 这个里面说的情况就是我所描述的情况,用可重入锁可以解决
程序员DMZ 2019-07-22
  • 打赏
  • 举报
回复
用可重入锁应该就可以了,a方法获取锁后,在方法内部的b方法不用再获取锁
angel6709 2019-07-22
  • 打赏
  • 举报
回复
尽管在b中加锁就是了。
LvBao_117 2019-07-19
  • 打赏
  • 举报
回复
学习了,收藏mark
秋的红果实 2019-07-19
  • 打赏
  • 举报
回复
若允许重新设计的话,让method1和method2独立并行,用async/await实现“同步” 有时间的大侠讨论下,不知道是不是我理解的这样
秋的红果实 2019-07-19
  • 打赏
  • 举报
回复
楼主曲解了问题,不是你代码写的那种场景 我觉得是这样

//A():
Object obj=new Object();
lock(obj)
{
    method1(互斥资源);
    B();
}

private void B()
{
    method2(互斥资源);
}

问题:如果A,B是并行线程,如何解决问题? 如果是单线程,就按照上面方法执行,没问题的
wanghui0380 2019-07-19
  • 打赏
  • 举报
回复
引用 12 楼 橘子皮zzz 的回复:
对,楼主代码理解错了,肯定不是操作data啊。data怎么能操作呢


data当然能操作,所以会建议写出 静态只读。当然lock要求data是引用对象,所以呢,正常静态只读归静态只读,但是可以对他进行操作,比如调用方法,添加,删除集合元素


回到问题本身,lock到底是什么??lock是同步锁,涉及的问题在于线程间同步问题,lock到底锁了啥?其实lock锁的是,线程对变量引用的临界,线程上下文,,申请同步对象,这个锁其实锁的就是他,别人在“申请同步”,其他线程请等待这个人释放临界。所以不是说操作他就死锁。
死锁发生在A申请一个,B正在使用的东西,而B同时申请一个A在使用的东西,他们谁都申请不到,他又谁都不肯释放

比如现在车多,我经常看到,两司机会车,就堵那里,谁都不让。这就是死锁。

解决办法,只要有个人让让就行了。

橘子皮... 2019-07-19
  • 打赏
  • 举报
回复
对,楼主代码理解错了,肯定不是操作data啊。data怎么能操作呢

糯米粽子1218 2019-07-18
  • 打赏
  • 举报
回复
引用 1 楼 正怒月神 的回复:
看起来好像死锁了吧
我当时想的也是这个,在B了死锁了,但是面试官问我解决方案,没回答上来,不过也没说用的是lock,只是说用锁,我不知道用其他类型的锁是否能实现这种需求
糯米粽子1218 2019-07-18
  • 打赏
  • 举报
回复
引用 5 楼 wanghui0380 的回复:
只要知道他是临界控制,不是什么读写控制。这个问题就不言而喻了 就像说”我宣布这块土地归我所有“---------那么我自己在我自己的地盘上当然可以自由的玩。 临界控制,控制的是线程间并发,而不是你自己。你自己没有并发,你自己的代码都是串行执行的代码。他lock不是不让人操作,而是不让别人操作。
没有明确说是单个线程的场景,有可能是不同的线程同时访问,即A和B出于两个线程,资源data是全局资源
正怒月神 2019-07-18
  • 打赏
  • 举报
回复
引用 4 楼 wanghui0380 的回复:
[quote=引用 1 楼 正怒月神 的回复:] 看起来好像死锁了吧
没有死锁,理由已经说明,他对本线程可重入[/quote] 我认为既然谈到锁,应该是多线程的分开执行A和B吧。
wanghui0380 2019-07-18
  • 打赏
  • 举报
回复
只要知道他是临界控制,不是什么读写控制。这个问题就不言而喻了 就像说”我宣布这块土地归我所有“---------那么我自己在我自己的地盘上当然可以自由的玩。 临界控制,控制的是线程间并发,而不是你自己。你自己没有并发,你自己的代码都是串行执行的代码。他lock不是不让人操作,而是不让别人操作。
wanghui0380 2019-07-18
  • 打赏
  • 举报
回复
引用 1 楼 正怒月神 的回复:
看起来好像死锁了吧
没有死锁,理由已经说明,他对本线程可重入
wanghui0380 2019-07-18
  • 打赏
  • 举报
回复
lock是对本线程是可重入的。 但是你的表述有问题,有一个跟基本的观念你还没弄清楚,lock跟什么读写data没有啥关系,lock只是临界控制,不是什么读写data。
正怒月神 2019-07-18
  • 打赏
  • 举报
回复
你可以设置超时放弃。
正怒月神 2019-07-18
  • 打赏
  • 举报
回复
看起来好像死锁了吧

110,537

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧