본문 바로가기

FrontEnd/C#

The C# Programing Language 2장

2장

 

5. 전처리 지시문

 

* 전처리란?

실질적인 컴파일 이전에 미리 처리되는 문장을 가리키며 선행처리기라고도 한다.

따라서 컴파일러는 사용자가 작성한 코드를 컴파일 하기전에 전처리문에서 정의해놓은 작업들을 먼저 수행한다.

전처리를 처리하는 처리기를 전처리기(preprocessor)라 하고 전처리에 사용되는 작업지시어를

전처리 지시어(preprocessing directive)라 한다.

 

 처리 지시문은 소스 파일의 특정 부분을 조건적으로 건너뛰고

에러나 경고 조건을 보고하며, 소스코드의 다른 부분을 나타내는 기능을 제공한다.

'전처리 지시문'이란 용어는 C와 C++프로그래밍 언어와의 일관성을 위해서만 사용한다.

C#에서는 별도의 전처리 단계가 없고, 전처리 지시문은 어휘 분석 단계의

일부로 처리된다.

 

- #define과 #undef : 조건부 컴파일 기호를 정의하고 정의를 해제할 때 사용한다.

- #if와 #elif, #else, #endif : 조건에 따라 소스코드의 특정 부분을 건너 뛸 때 사용한다.

- #line : 에러나 경고에 나오는 줄 번호를 제어할 때 사용한다.

- #error와 #warning : 에러와 경로를 일으킬 때 사용한다.

- #region과 #endregion : 소스코드의 특정 부분을 명시적으로 표시하는 데 사용된다.

- #pragma 컴파일러에 선택적인 상황 정보를 지정하는 데 사용한다.

 

전처리지시문이 포함된 소스에서는 한 줄 주석만 사용이 가능하다.

 

1) 조건부컴파일 기호(#if, #elif, #else, #endif)

조건부 컴파일 기호는 정의됨이나 정의되지 않음을 나타내는 두 가지 상태가 있다.

소스 파일의 어휘 처리 초기에 조건부 컴파일 기호는 커맨드라인 컴파일러 옵션과

같은 외부 메커니즘으로 명시적인 정의를 하지 않는 한 정의되지 않은 상태다.

#define 지시문이 처리될 때 지시문에서 명명한 조건부 컴파일 기호는

해당 소스파일에서 정의된다.

이 기호는 동일한 기호에 대한 #undef 지시문이 처리될 때 까지,

또는 소스파일의 마지막에 도달하기 전까지 정의된 상태로 존재한다.

이것의 의미는 한 소스 파일에 있는 #define과 #undef 지시문이 동일한 프로그램 내의

다른 소스 파일에 영향을 주지 않는다.

 

전처리 표현식에서 참조될 때 정의된 조건부 컴파일 기호의 불리언값은 true이며,

정의되지 않은 조건부 컴파일 기호의 불리언 값은 false이다.

전처리 표현식에서 조건부 컴파일 기호를 참조하기 전에 이러한 조건부 컴파일 기호를 명시적으로 선언할 필요는 없다.

대신 선언하지 않은 기호는 단순히 정의되지 않은 기호이므로 그 값은 false이다.

조건부 컴파일 기호의 네임스페이스는 C# 프로그램에서 고유하며, 다른 모든 명명 된

엔티티와 분리된다. 조건부 컴파일 기호는 #define과 #undef 지시문과 전처리표현식 내에서만 참조할 수 있다.

 

2) 전처리 표현식

전처리 표현식은 #if와 #else 지시문에서 사용할 수 있다.

!와 ==, !=, &&, || 연산자는 전처리 표현식에 사용할 수 있으며, 괄호를 사용해 묶을 수 있다.

 

3) 선언 지시문

선언 지시문을 사용해 조건부 컴파일 기호를 정의하거나 정의를 해제한다.

#define 지시문을 처리하면 지정한 조건부 컴파일 기호는 해당 지시문 다음의 소스 줄로부터 정의된 상태가 된다.

마찬가지로 #undef 지시문을 처리하면 해당 지점부터 뒤의 소스에는 정의되지 않은 상태가 된다.

#define과 #undef 지시문은 소스 파일의 첫 번째 토큰앞에 와야한다.

그렇지 않으면 컴파일 에러가 발생한다.

 

4) 조건부 컴파일 지시문

조건부 컴파일 지시문을 사용해 소스 파일의 일부를 조건적으로 포함하거나 제외한다.

조건부 컴파일 지시문은 #if 지시문, 0개 이상의 #elif지시문, 0개 이상의 #else 지시문,

#endif 지시문을 차례로 사용해 작성해야 한다.

지시문 사이에는 소스코드의 조건 섹션이 온다.

각 센션은 바로 앞에 있는 지시문으로 제어한다.

조건 섹션은 제공된 중첩된 조건부 컴파일 지시문을 담을 수 있는데,

이 때 이들 지시문은 완전한 집합을 구성해야 한다.

 

-  #if와 #elif 지시문의 전처리 표현식 집합은 하나가 true를 생성 할때까지 차례로 평가된다.

한 표현식이 true가 되면 해당 지시문의 조건 섹션이 선택된다.

- 모든 전처리 표현식 집합이 false를 생성하고, #else 지시문이 있으면 #elseㅈ시문의 조건 섹션이 선택된다.

- 그렇지 않으면 선택되는 조건 섹션은 없다.

 

선택 된 조건 섹션이 있다면 정산적인 입력 섹션으로 처리된다.

이 섹션에 포함된 소스코드는 어휘 문법에 맞아야 하므로, 토큰은 이 섹션 내의 소스코드에서 생성된다.

이 센션 내의 전처리 지시문은 규정된 효력을 낸다.

 

5) 진단 지시문

간단 지시문을 사용해 다른 컴파일 에러와 경고가 발생하는 방법과 동일한 방법으로 보고되는 에러와 경고 메시지를 명시적으로 생성시킬 수ㅜ 있다.

 

6) 영역 지시문

영역 지시문을 사용해 소스코드의 득정 영역을 명시적으로 표시할 수 있다.

 

영역에 특별한 의미를 부여하지 않는다.

영역으 프로그래머나 자동화 도구가 소스코드의 섹션을 표시하는 용도로만 사용한다.

#region이나 #endrigion 지시문에 지정한 메시지에는 특별한 의미가 없다.

이러한 메시지는 영역을 식별하기 위해서만 사용한다.

#region과 @endrigion 지시문을 같이 사용하면 다른 전처리 메시지가 올 수 있다.

 

7) 줄 지시문

줄 시지문을 사용해 컴파일러에서 경고와 에러 같은 출력으로 보고하는 줄 번호와 소스 파일 이름을 변경할 수 있다.

줄 지시문은 다른텍스트 입력에서 C# 소스코드를 생성하는 메타 프로그래밍 도구로 가장 널리 사용하는 지시문이다.

 

#line지시문이 없을 때 컴파일러는 출력에 원래의 줄 번호와 소스 파일 이름을 보고한다.

default가 아닌 줄 지시자응 포함하는 #line 지시문을 처리 할 때 컴파일러는 지시문 뒤의 줄에

줄 번호(지정된 경우 파일 이름도)를 지정한 것처럼 취급한다.

 

#line default 지시문은 앞서의 몯ㄴ #line 지시문 결과를 되돌린다.

컴파일러는 정확하게 어떠한 #line 지시문도 처리되지 않은 것처럼 이후의 줄들의 줄들에 대해

원래 줄 정보를 보고한다.

#line hidden지시문은 에러 메시지에 보고되는 파일과 줄 번호에는 영향을 주지 않지만,

소ㅡ 수준 디버깅에는 영향을 끼친다.

디버깅할 때 #line hidden 지시문과 다름 #line 지시문 사이의 모든 줄에 줄 번호 정보다 없다.

디버거에서 코드를 단계별로 실행할 때 이들 줄은 모두 건너뛴다.

파일이름은 이스케이프 문자가 처리되지 않는다는 점에서 보통의 문자열 리터럴과 다르다.

 

8) pragma 지시문

#pragma 전처리 지시문은 선택적인 맥락 정보를 컴파일러레 지정하는데 사용한다.

#pragma 지시문에서 제공하는 정보에서 프로그램 구문은 전혀 변경하지 않는다.

 

C#은 #pragma 지시문을 제공해 컴파일러 경고를 제어한다.

언어의 향후 버전에서는 추가적인 #paragma 지시문들이 포함될 수도 있다.

마이크로소프트는 C# 컴파일러는 다른 C# 컴파일러들과의 상호운용성을 보장하기 위해

알렺지 않은 #pragma 지시문에 대한 컴파일 에러는 일으키지 않는다.

하지만 그런 지시문의 경우 경고는 표시한다.

 

8-1) Pragma 경고

#pragma warning 지시문을 사용해 이후의 프로그램 텍스트를 컴파일 하는동안 전부 또는 특정 경고 메시지의

집합을 해제하거나 복원한다.

 

경고목록을 생략한 #pragma warning 지시문은 모든 경고에 영향을 미친다.

경고 목록을 포함하는 #pragma warning 지시문은 해당 목록에서 지정한 경고에만 영향을 준다.

 

#pragma warning diable 지시문은 전부 또는 지정된 경고 집합을 해제한다.

#pragma warning restore 지시문은 전부 또는 지정된 경고 집합을 사실상 초기 컴파일 단위였던 상태로 복원한다.

특정 경고가 외부적으로 해제됐다면 전부 또는 지정된 경고 여부에 따라 #pragma warning restore는 그 경고를 다시 활성화 시키지 않는다

 

 

'FrontEnd > C#' 카테고리의 다른 글

C# Winform 간 핸들링  (0) 2013.07.03
C# Chart (Line) 실시간 반영  (0) 2013.07.01
The C# Programing Language 4장  (0) 2012.08.03
The C# Programing Language 3장  (0) 2012.08.03
The C# Programing Language 1장  (0) 2012.07.25