다음을 통해 공유


Volatile 클래스

정의

휘발성 메모리 작업을 수행하기 위한 메서드를 포함합니다.

public ref class Volatile abstract sealed
public static class Volatile
type Volatile = class
Public Class Volatile
상속
Volatile

설명

다중 프로세서 시스템에서는 컴파일러 또는 프로세서의 성능 최적화로 인해 여러 프로세서가 동일한 메모리에서 작동할 때 일반 메모리 작업이 다시 정렬되는 것처럼 보일 수 있습니다. 휘발성 메모리 작업은 작업과 관련하여 특정 유형의 재정렬을 방지합니다. 휘발성 쓰기 작업은 스레드의 이전 메모리 작업이 휘발성 쓰기 후에 발생하도록 다시 정렬되지 않도록 합니다. 휘발성 읽기 작업은 스레드의 이후 메모리 작업이 휘발성 읽기 전에 발생하도록 다시 정렬되지 않도록 합니다. 이러한 작업에는 성능에 영향을 줄 수 있는 일부 프로세서의 메모리 장벽이 포함될 수 있습니다.

예를 들어 스레드 2개와 필드 xy 2 Int32 개가 있고 처음에는 0인 다음 시나리오를 고려해 보세요.

스레드 1 스레드 2
x = 1; int y2 = Volatile.Read(ref y);
Volatile.Write(ref y, 1); int x2 = x;

휘발성 읽기 및 쓰기는 컴파일러 또는 프로세서와 같이 각 스레드 내에서 두 작업의 순서를 다시 정렬하지 못하도록 합니다. 스레드가 다른 프로세서에서 실행될 수 있는 다중 프로세서 시스템에서도 이러한 작업이 실제로 다른 스레드를 기준으로 한 스레드에서 발생하는 순서에 관계없이 휘발성 연산은 스레드 2에 및 x2 == 0가 표시되지 y2 == 1 않도록 보장합니다. 스레드 1에서 에 x 대한 쓰기는 에 대한 휘발성 쓰기 y전에 발생해야 하며 스레드 2에서는 의 휘발성 읽기 y후에 의 x 읽기가 발생해야 합니다. 따라서 스레드 2에 가 표시 y2 == 1되면 도 표시됩니다 x2 == 1.

그러나 작업이 발생하는 특정 시퀀스와 위와 동일한 시나리오를 고려합니다.

시퀀스 스레드 1 스레드 2
1 x = 1; ...
2 Volatile.Write(ref y, 1); ...
3 ... int y2 = Volatile.Read(ref y);
4 ... int x2 = x;

스레드 1에서 에 대한 휘발성 쓰기 y 가 스레드 2에서 의 y 휘발성 읽기 전에 발생했지만 스레드 2는 여전히 를 볼 y2 == 0수 있습니다. 에 대한 휘발성 쓰기 y 는 다른 프로세서에서 다음 휘발성 읽기 y 가 업데이트된 값을 볼 수 있음을 보장하지 않습니다.

참고

  • 휘발성 읽기 및 쓰기는 값이 메모리에 읽거나 쓰여지고 캐시되지 않도록 합니다(예: 프로세서 레지스터). 따라서 이러한 작업을 사용하여 다른 스레드 또는 하드웨어에서 업데이트할 수 있는 필드에 대한 액세스를 동기화할 수 있습니다.
  • 클래스는 Volatile 및 와 같은 Int64 일부 64비트 형식에 대한 읽기 및 Double쓰기 작업도 제공합니다. 이러한 64비트 메모리에 대한 휘발성 읽기 및 쓰기는 일반 읽기 및 쓰기와 달리 32비트 프로세서에서도 원자성입니다.

휘발성 메모리 작업은 일반적인 잠금이 허용 가능한 대안이 아닌 특별한 동기화의 경우를 위한 것입니다. 정상적인 상황에서는 C# lock 문, Visual Basic SyncLock 문 및 Monitor 클래스가 데이터에 대한 액세스를 동기화하는 가장 쉽고 오류가 발생하기 쉬운 방법을 제공하며 Lazy<T> , 클래스는 이중 확인 잠금을 직접 사용하지 않고도 지연 초기화 코드를 작성하는 간단한 방법을 제공합니다.

Volatile.Write 메서드는 Volatile.Read 언어에서 지원되지 않는 기능을 사용하도록 설정합니다. 예를 들면 다음과 같습니다.

  • Visual Basic과 같은 일부 언어는 휘발성 메모리 작업의 개념을 인식하지 않습니다. 클래스는 Volatile 이러한 언어로 해당 기능을 제공합니다.

    참고

    이러한 메서드 중 하나를 호출하면 단일 메모리 액세스에만 영향을 줍니다. 필드에 대한 효과적인 동기화를 제공하려면 필드에 대한 모든 액세스 권한이 및 Volatile.Write를 사용해야 Volatile.Read 합니다.

  • C#에서 필드에 한정자를 사용하면 volatile 해당 필드에 대한 모든 액세스가 휘발성 메모리 작업이지만 volatile 배열 요소에 한정자를 적용할 수 없습니다. 및 Volatile.Write 메서드는 Volatile.Read 배열 요소에 사용할 수 있습니다.

메서드

Read(Boolean)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(Byte)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(Double)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(Int16)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(Int32)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(Int64)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(IntPtr)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(SByte)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(Single)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(UInt16)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(UInt32)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(UInt64)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read(UIntPtr)

지정된 필드의 값을 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Read<T>(T)

지정된 필드에서 개체 참조를 읽습니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 뒤에 나타나는 경우 프로세서가 이 메서드 앞으로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(Boolean, Boolean)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(Byte, Byte)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(Double, Double)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(Int16, Int16)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(Int32, Int32)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(Int64, Int64)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(IntPtr, IntPtr)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(SByte, SByte)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(Single, Single)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(UInt16, UInt16)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(UInt32, UInt32)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(UInt64, UInt64)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write(UIntPtr, UIntPtr)

지정된 필드에 지정된 값을 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

Write<T>(T, T)

지정된 필드에 지정된 개체 참조를 씁니다. 필요한 시스템에서는 프로세서가 메모리 작업을 다시 정렬하는 것을 막는 메모리 차단을 다음과 같이 삽입합니다. 코드에서 읽기 또는 쓰기가 이 메서드 앞에 나타나는 경우 프로세서가 이 메서드 뒤로 읽기 또는 쓰기를 이동할 수 없습니다.

적용 대상

추가 정보