Чтение и запись в общую память занимает ограниченный период времени, поэтому они могут либо перекрываться, либо полностью различаться.
, например
Thread 1: wwwww wwwww
Thread 2: rrrrr rrrrr
Thread 3: rrrrr rrrrr
Первое чтение из потока 2 перекрывается с первой записью из потока 1, тогда как второе чтение и вторая запись не перекрываются. В потоке 3 оба чтения перекрывают первую запись.
Регистр
A safe безопасен только при чтениях, которые не перекрывают записи. Если чтение не перекрывает записи, оно должно прочитать значение, записанное самой последней записью. В противном случае он может вернуть любое значение, которое может содержать регистр. Таким образом, в потоке 2 второе чтение должно возвращать значение, записанное второй записью, но первое чтение может вернуть любое допустимое значение.
A обычный регистр добавляет дополнительную гарантию того, что если чтение перекрывается с записью, то оно будет либо читать старое значение, либо новое, но множественные чтения, которые перекрывают запись, не должны согласовывать который, и значение может показаться «мерцающим» взад и вперед. Это означает, что два чтения из одного и того же потока (например, из потока 3 выше), которые оба перекрывают запись, могут выглядеть «не по порядку»: более раннее чтение возвращает новое значение, а позднее возвращает старое значение.
Регистр atomic гарантирует, что чтение и запись, по-видимому, происходят в один момент времени. Читатели, которые действуют в точке до этой точки, будут все читать старое значение, а читатели, которые действуют после этой точки, будут читать новое значение. В частности, если два чтения из одного и того же потока перекрывают запись, то позднее чтение не может вернуть старое значение, если более раннее чтение возвращает новое. Атомные регистры линеаризуемы .
Искусство многопроцессорного программирования Мориса Херлихи и Нира Шавита дает хорошее описание, а также примеры и варианты использования.