VB.net 是作为原子块执行的一行代码

In VB.net Is A Line Of Code Executed As An Atomic Block

提问人:CodeAdze 提问时间:4/17/2023 更新时间:4/17/2023 访问量:67

问:

我正在尝试学习和使用更多的异步代码,但让自己对原子执行和不执行的内容感到困惑。

    Private Sub PublishUpdateNotification()
        If Interlocked.Increment(WaitingThreadCount) > 1 Then Exit Sub
        Task.Run(Sub() DeliverTheNotifications())
    End Sub

    Private Shared Readonly Property WaitingThreadCount as Integer = 0
End Class

在上面的代码片段中,如果该方法由两个线程调用,则该行是否会作为原子块执行,或者在第一个线程递增之后但在测试其值之前是否会发生上下文切换,从而允许第二个线程也增加含义两个语句都将针对值 2 进行测试,并且都将退出 sub,这不是我的意图。If Interlocked.Add(...WaitingThreadCountWaitingThreadCountValueIf

我需要在 a 中做这个测试吗?Synclock

提前致谢。

vb.net 多线程异 锁定 原子

评论

0赞 jmcilhinney 4/17/2023
您是否在问增量和比较是否会以原子方式执行?
0赞 dbasnett 4/17/2023
@CodeAdze - Interlocked.Increment(WaitingThreadCount) 递增指定的变量并将结果存储为原子操作。测试不是原子操作的一部分。没有多少线程可以执行 Increment 并返回相同的值。
0赞 Craig 4/17/2023
关于你的最后一个问题...您可能希望优先使用过度无锁的方法(如 ),直到分析显示锁定是瓶颈。您不仅需要担心以原子方式执行的内容,还可能需要担心内存访问的重新排序,特别是如果您希望以内存排序比 x86 系列更弱的处理器为目标。SyncLockInterlocked.Increment
1赞 Craig 4/17/2023
这里有一个链接可以帮助您入门:ericlippert.com/2014/03/26/reordering-optimizations
2赞 dbasnett 4/17/2023
@CodeAdze - 比较将是该特定线程增量时的值。如果这是你所想的,就没有干预阅读。如果这就是所有代码,我不会使用任何线程锁定机制。

答:

0赞 dbasnett 4/17/2023 #1

FWIW(英语:FWIW)

Private Sub PublishUpdateNotification()
    If Interlocked.Increment(WaitingThreadCount) <= 1 Then
        Task.Run(Sub() DeliverTheNotifications())
    End If
End Sub