Скажем, у вас есть простой класс:
class MyClass
{
private readonly int a;
private int b;
public MyClass(int a, int b) { this.a = a; this.b = b; }
public int A { get { return a; } }
public int B { get { return b; } }
}
Я мог бы использовать этот класс многопоточным образом:
MyClass value = null;
Task.Run(() => {
while (true) { value = new MyClass(1, 1); Thread.Sleep(10); }
});
while (true)
{
MyClass result = value;
if (result != null && (result.A != 1 || result.B != 1)) {
throw new Exception();
}
Thread.Sleep(10);
}
Мой вопрос: буду ли я когда-либо видеть этот (или другой похожий многопоточный код), вызывать исключение? Я часто вижу ссылку на тот факт, что энергонезависимая запись не может быть немедленно замечена другими потоками. Таким образом, похоже, что это может потерпеть неудачу, потому что запись в поле значения может произойти до записи в и b. Возможно ли это, или есть что-то в модели памяти, которая делает этот (довольно распространенный) шаблон безопасным? Если так, то, что это? Имеет ли значение только для этой цели? Имеет ли значение, если a и b являются типом, который не может быть атомарно написан (например, пользовательская структура)?