ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

简单的线程问题,锁定对共享资源或整个功能的访问?

2019-11-03 00:05:30  阅读:210  来源: 互联网

标签:critical-section multithreading locking c net


这是我之前提出的一个问题的解释.这是一个简单的线程问题,但我似乎无法理解.

如果我有共享代码:

private static object objSync = new object();
private int a = 0;

    public void function()
    {
    lock(objSync)
      a += 2;

    lock(objSync)
      a += 3;
    Console.WriteLine(a.ToString());
    a=0;
    }

我不能期望最后的“ a”等于5,因为第一个线程获得的锁将“ a”设置为2,然后下一个线程可以在第一个线程能够将锁设置为“ 4”之前获得锁.加3,最后得到7.

据我了解,解决方案是在整个事情上加一个锁,然后您总是可以期望得到5.现在我的问题是,如果两个锁之间有一百万行代码,那该怎么办.我无法想象要锁定一百万行代码.您如何通过在大约一百万行和两行代码之间加一个锁来确保线程安全,但又不会导致性能下降?

编辑:

这是我为该问题编写的废话代码.实际应用是线路监控系统.有两个显示当前行的屏幕,一个显示给文员,另一个显示给公众.职员的屏幕通过串行端口接受“点击”,从而使行前进一格,然后通过notify事件更新公共屏幕(请参阅观察者设计模式).问题是,如果您向答题器发送垃圾邮件,它们将不会同步.我想象发生了什么事,就是第一个屏幕被添加到行号中,显示它,然后更新公共屏幕,但是在公共屏幕有机会显示数据库中的行号之前,业务员再次单击并且该行号消失了同步上面的“ a”代表我从数据库中检索到的值,而不仅仅是一个简单的int值.我在几个地方更改了值,我需要所有这些都自动发生.

解决方法:

这完全取决于您定义的“成功”.如果这是一个计数器,那可能仍然是正确的结果.如果只想按原样更新它,则在第一个锁中拍摄快照,然后与最终锁中的快照进行比较.在那种情况下,您可以用一些Interlocked.CompareExchange替换许多代码.同样在“计数器”方案中,Interlocked.Increment是您的朋友.

如果代码必须匹配,那么您有几个选择:

>如果比较失败,请再次运行整百万行;重复直到赢得比赛(通过匹配)
>如果比较失败,则引发异常
>封锁百万条线路;可能仍然是一百万行…
>考虑其他适合您情况的解决策略

在前两个中,您应该通过将任何相关数据置于中间状态来监视污染情况.

顺便说一句最终分配给0可能也应该是同一锁定策略的一部分.只有所有访问都尊重锁,锁才起作用.

但是只有您的情况可以告诉我们冲突中的“正确”行为是什么.

标签:critical-section,multithreading,locking,c,net
来源: https://codeday.me/bug/20191102/1995204.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有