Reading an int that's updated by Interlocked on other threads

前端 未结 4 1488
终归单人心
终归单人心 2020-12-05 00:21

(This is a repeat of: How to correctly read an Interlocked.Increment'ed int field? but, after reading the answers and comments, I\'m still not sure of the right answer.)

4条回答
  •  不思量自难忘°
    2020-12-05 00:52

    Thread.VolatileRead(numberOfUpdates) is what you want. numberOfUpdates is an Int32, so you already have atomicity by default, and Thread.VolatileRead will ensure volatility is dealt with.

    If numberOfUpdates is defined as volatile int numberOfUpdates; you don't have to do this, as all reads of it will already be volatile reads.


    There seems to be confusion about whether Interlocked.CompareExchange is more appropriate. Consider the following two excerpts from the documentation.

    From the Thread.VolatileRead documentation:

    Reads the value of a field. The value is the latest written by any processor in a computer, regardless of the number of processors or the state of processor cache.

    From the Interlocked.CompareExchange documentation:

    Compares two 32-bit signed integers for equality and, if they are equal, replaces one of the values.

    In terms of the stated behavior of these methods, Thread.VolatileRead is clearly more appropriate. You do not want to compare numberOfUpdates to another value, and you do not want to replace its value. You want to read its value.


    Lasse makes a good point in his comment: you might be better off using simple locking. When the other code wants to update numberOfUpdates it does something like the following.

    lock (state)
    {
        state.numberOfUpdates++;
    }
    

    When you want to read it, you do something like the following.

    int value;
    lock (state)
    {
        value = state.numberOfUpdates;
    }
    

    This will ensure your requirements of atomicity and volatility without delving into more-obscure, relatively low-level multithreading primitives.

提交回复
热议问题