static 키워드

static 키워드 (C# 참조)

이 문서는 static 한정자(modifier) 키워드를 다뤄요. static 키워드는 using static 지시문의 일부로도 쓰이죠.

static 한정자를 쓰면 정적 멤버(static member) 를 선언할 수 있어요. 정적 멤버는 특정 객체가 아니라 타입 자체에 속하는 멤버예요. 또 static 한정자로 static 클래스를 선언할 수도 있고요. 클래스(class), 인터페이스(interface), 구조체(struct)에서는 필드, 메서드, 프로퍼티, 연산자, 이벤트, 생성자에 static 한정자를 붙일 수 있어요. 다만 인덱서(indexer)나 종료자(finalizer)에는 붙일 수 없답니다. 자세한 내용은 Static Classes and Static Class Members를 참고해 주세요.

로컬 함수(local function)에도 static 한정자를 붙일 수 있어요. static 로컬 함수는 지역 변수나 인스턴스 상태를 캡처할 수 없어요.

:::code language="csharp" source="./snippets/csrefKeywordsModifiers.cs" id="28":::

람다 식(lambda expression)이나 익명 메서드(anonymous method)에도 static 한정자를 붙일 수 있어요. static 람다나 익명 메서드 역시 지역 변수나 인스턴스 상태를 캡처하지 못해요.

:::code language="csharp" source="./snippets/csrefKeywordsModifiers.cs" id="29":::

아래 클래스는 static으로 선언됐고, static 메서드만 담고 있어요.

:::code language="csharp" source="./snippets/csrefKeywordsModifiers.cs" id="18":::

상수(constant)나 타입 선언은 암시적으로 static 멤버예요. static 멤버는 인스턴스를 통해서는 참조할 수 없고, 대신 타입 이름으로 참조해야 해요. 예를 들어 다음 클래스를 볼게요.

:::code language="csharp" source="./snippets/csrefKeywordsModifiers.cs" id="19":::

static 멤버 x를 참조하려면, 그 멤버가 같은 스코프에서 접근 가능한 경우가 아니라면 정규화된 이름 MyBaseC.MyStruct.x를 사용해야 해요.

Console.WriteLine(MyBaseC.MyStruct.x);

클래스의 인스턴스는 그 클래스의 모든 인스턴스 필드를 각각 별도의 복사본으로 가지지만, static 필드는 하나뿐이에요. 제네릭 타입의 경우 각각의 닫힌 제네릭 타입(closed generic type)이 자신만의 static 필드 복사본을 가져요. 그리고 xref:System.ThreadStaticAttribute로 표시된 static 필드는 스레드마다 하나씩 가진답니다.

static 메서드나 프로퍼티 접근자에서 this를 사용할 수는 없어요.

클래스에 static 키워드를 적용하면, 그 클래스의 모든 멤버는 반드시 static이어야 해요.

클래스, 인터페이스, static 클래스는 static 생성자를 가질 수 있어요. static 생성자는 프로그램이 시작된 시점과 클래스가 인스턴스화되는 시점 사이 어느 때에 호출돼요.

[!NOTE] C++의 static 키워드와 비교하면 C#에서는 용도가 훨씬 제한적이에요. C++ 키워드와의 비교는 Storage classes (C++)를 참고해 주세요.

static 멤버가 왜 필요한지, 회사 직원을 나타내는 클래스를 예로 들어볼게요. 이 클래스에 직원 수를 세는 메서드와 직원 수를 저장하는 필드가 있다고 해볼게요. 이 메서드와 필드는 어느 한 직원 인스턴스에 속하지 않아요. 대신 직원 전체 클래스에 속하죠. 그래서 이 둘은 클래스의 static 멤버로 선언돼야 해요.

이 예제는 새 직원의 이름과 ID를 읽고, 직원 카운터를 하나 증가시킨 뒤, 새 직원의 정보와 새 직원 수를 보여줘요. 프로그램은 현재 직원 수를 키보드에서 읽어요.

:::code language="csharp" source="./snippets/csrefKeywordsModifiers.cs" id="20":::

static 필드를 아직 선언되지 않은 다른 static 필드로 초기화할 수 있다는 것도 보여줄게요. 이때 결과는 그 static 필드에 값을 명시적으로 할당하기 전까지는 정의되지 않아요.

:::code language="csharp" source="./snippets/csrefKeywordsModifiers.cs" id="21":::

C# 언어 사양

[!INCLUDECSharplangspec]

더 알아보기