C 언어와 C++ 언어에서 const 처리.
C 언어와 C++ 언어에서 'const' 처리는 조금 다릅니다. :shocked:?
일단 C 언어의 경우, 32, 012, 0x3 등은 정수 상수입니다 (integer constant). 또는 정수 상수식 (integer constant expression)이라고도 합니다. 가변 배열을 제외하고, 배열 크기를 써 준다거나, struct bit-field로 지정할 수 있는 수치는 모두 정수 상수식이어야 합니다.
const int ci = 3
에서, 변수 ci의 타입은 const int입니다. 보통 이런 식으로 'const'가 붙은 타입을 const-qualified type이라고 합니다. 그리고 const-qualified type의 오브젝트는 정수 상수가 아닙니다. 따라서 (가변 배열을 제외하고) 배열의 크기를 지정할 때 ci를 쓴다거나, case 레이블로 쓸 수 없습니다.
C++ 언어 경우, 정수 상수, 정수 상수식 등은 C 언어와 같습니다. 단. const-qualified type의 오브젝트는 정수 상수가 됩니다. 따라서 const int 등으로 선언한 것도 정수 상수 취급을 받아서 배열의 크기를 지정한다거나 case 레이블로 쓸 수 있습니다.
const가 붙은 오브젝트... 말이 좀 이상하죠? 아무리 생각해 봐도 좀 더 나은 표현은 "처음 값을 지정할 때를 제외하고 값을 변경할 수 없는 오브젝트"가 더 나은 표현일 것 같긴 한데.. 그렇다고 상수라고 표현하기 곤란한 게, 이것과 정수 상수와는 전혀 다른 뜻이기 때문에... :sad:
또, C/C++ 모두, const-qualified type으로 선언한 변수는 직/간접적으로 그 값을 변경하면 안됩니다. 이는 undefined behavior에 속합니다. 다음과 같은 코드를 보면 무슨 말인지 쉽게 알 수 있을 것입니다:
const int i = 3; int *p = (int *)&i; *p = 4; /* wrong: undefined behavior */
여담으로 C++에서 위와 같이 C 스타일 타입 변환보다, const_cast를 쓰는 것이 더 바람직합니다.
포인터 선언할 때, const의 위치에 따라서 다양한 종류가 나올 수 있습니다.
1. const int *cip (또는 int const *ip) 2. int * const icp 3. const int * const cicp (또는 int const * const ip)
첫번째는 const int를 가리키는 포인터 ip입니다. 즉 const qualified int (값을 바꿀 수 없는 정수 타입)을 가리키는 포인터입니다. 이 포인터는 얼마든지 다른 const int를 가리키도록 바꿀 수 있지만, 가리키고 있는 대상의 값을 바꿀 수는 없습니다.
const int ci1 = 4, ci2 = 8; const int *cip = &ci1; cip = &ci2; /* ok */ *cip = 0; /* wrong */
두번째는 일반 정수 타입 int를 가리키는 const 포인터입니다. 즉, 가리키는 대상이 int이기 때문에, 얼마든지 값을 변경할 수 있지만, 포인터 자체가 const이기 때문에 다른 int를 가리키도록 바꿀 수 없습니다.
int i1 = 4, i2 = 8; int * const icp = &i1; icp = &i2; /* wrong */ *icp = 0; /* ok */
세번째는 const int를 가리키는 const 포인터입니다. 따라서 다른 대상을 가리키도록 포인터를 바꿀 수도 없고, 대상이 가지고 있는 값을 바꿀 수도 없습니다.
const int ci1 = 3, ci2 = 4; const int * const cicp = &ci1; cicp = &ci2; /* wrong */ *cicp = 0; /* wrong */
참고: ISO C 표준 Sec. 6.7.3.5
참고: ISO C++ 표준 Sec. 5.2.11.7, Sec. 7.1.5.1
고맙습니다. 도움이
고맙습니다. 도움이 많이 되었습니다. :)
----------------------------
May the F/OSS be with you..
C와 C++에서 const의
C와 C++에서 const의 또다른 차이점은 연결(linkage)이죠.
C에서는 블럭 외부에 선언된 const 개체는 static을 붙이지 않으면 외부 연결을 갖습니다. 그런데 C++에서는 extern을 붙이지 않은 const 개체는 내부 연결을 갖지요. 따라서 C++에서는 const 개체의 정의를 헤더에 넣어도 one-definition rule을 위배하지 않습니다.
예를 들어 C의 경우 배열 크기를 헤더에서 #define으로 쓸 때가 많은데, C++에서는 이러한 매크로를 const 정수형으로 완벽하게 대체할 수 있다는 뜻이죠.
결론적으로 말하자면 C는 일관성을 추구하고 있고, C++은 일관성을 희생하면서 사용의 편의성을 높였다고 할 수 있겠습니다.
이런 사실이 또 있는지 몰랐네요. 좋은 정보 더
이런 사실이 또 있는지 몰랐네요.
좋은 정보 더 알아갑니다 ㅎㅎ
저는 이렇게 생각했습니다.
C, C++의 linkage 차이를
C, C++의 linkage 차이를 말씀하셨는데 차라리 const int 를 상수 정수와 같은 개념으로 쓴다고 정의된 것에 의한 것이 더 맞지 않을까 생각됩니다.
간단히 그냥 #define 의 전처리와 같지만 컴파일러 수준에서 관리해준다고 생각할 수도 있을 것 같네요.
미묘하군요...
C++ 학교에서만 잠깐 접했었는데... 미묘하군요..
좋은 정보 감사합니다.
2006년에 쓰신 글이 6년이나 지난 지금에도 제게 도움을 주고 있습니다.
감사드립니다 ㅎㅎ
저는 이렇게 생각했습니다.
감사합니다.
공들인 소중한 정보 잘 보겠습니다^^
고요한밤 거룩한밤 어둠에 묻힌밤
댓글 달기