상수포인터와 포인터상수의 차이
포인터와 배열을 배우다 보면 상수포인터와 포인터상수라는 용어를 많이 듣게 됩니다.
단어만 생각하면 순서만 바뀐 용어인데 뜻은 어떤지 알아볼까합니다.
/*
2014 9/19 추가부분
영어로 관련표현은
constant pointer - 포인터의 값이 상수인 포인터
pointer to constant - 상수를 가리키는 포인터
constant pointer to constant -상수를 가리키는 constant pointer
3가지입니다.
제가 여러책을 본 결과 한국어 번역으로 ,포인터상수와, 상수포인터는 번역상의 차이지 결국은 같은 의미로 혼용되고 있다고 생각이듭니다.어떤 책에서는 배열변수명이 포인터 상수라고하고 어떤 책에서는 상수포인터라고합니다. 어떤 책에서는 이에 대한 언급조차 되지 않고 있습니다.
/*
일반적으로 배열명을 포인터 상수라고 합니다. 이 설명은 포인터 변수(일반적인 포인터)와 대조해서 설명하기 위한 용어입니다.
이는 포인터 변수와 비슷하지만 상수적 특성을 나타낸다는 의미입니다.
다음을 살펴보겠습니다.
ar은 포인터상수이다.
위 배열의 선언에서 ar은 배열명입니다. 배열명은 배열 전체를 의미하기도 하지만 배열의 시작주소값을 나타내기도 합니다.
배열의 시작번지는 ar[0]의 주소값 &ar[0]입니다.
ar배열은 시작번지로부터 차례로 문자열의 요소를 하나씩 나타내는데 메모리상에서 각 요소들이 연속적으로 붙어있습니다.
메모리상에 연속적으로 붙어있기 때문에 ar이 가리키는 주소가 변하게 되면 배열정보가 엉망이 됩니다.
그래서 ar이 가리키는 주소를 못 바꾸게 하기 위해 배열생성부터 상수값으로 고정되어 있습니다.
그래서 배열명을 포인터 상수라고 합니다.
단 포인터 상수는 가리키는 주소값은 고정이지만 주소값이 가리키는 대상체는 얼마든지 바꿀 수 있습니다.
그럼 상수포인터를 알아봐야 하겠는데요, const에 대해 잠시 설명할까 합니다.
const는 변수를 상수화 시켜주는 키워드입니다.
#define도 특정 문자열을 상수화 시키지만 const와 다르게 전처리기에 의한 치환에의해 코드에 삽입된다는 것이 다릅니다.
const는 컴파일 상에서 지원해 주는데요. 일종의 추가되는 타입선언이라고 생각해도 무방합니다.
특징은 변수를 상수화 시키는 용도로 사용합니다.
사실 const는 컴파일러상에서 제공하는 안전장치로서, 컴파일러가 프로그래머가 실수하지않도록 도와주는 역할을 합니다.
코딩만 완벽하다면 없어도 된다는 이야기죠.
여기서 a는 상수지시포인터(pointer to constant)라고 합니다.
상수지시포인터는 상수를 가리키는 포인터라는 뜻으로 포인터 자체는 상수가 아닙니다.
그런데 이 const는 *를 기준으로 왼쪽 또는 오른쪽에 붙을때 마다 그 의미가 달라집니다.
위에 a는 상수지시포인터(pointer to constant),
아래 b는 상수포인터(constant pointer)라고 합니다. 상수 포인터는 포인터가 상수라는 의미입니다.(포인터가 가리키는 주소값을 바꿀 수 없음)
const의 위치에 따라서 의미하는 바가 다릅니다. 그리고 const키워드가 *좌우로 전부 붙는 경우는 상수지시상수포인터인데요, 이경우는 값도 주소값도 바꿀 수가 없습니다. 한마디로 얼음시켜 놓은거죠.
그리고 최신 컴파일러에선
이런 선언에 경고가 뜰 수가 있습니다.
그럴땐 선언에 const를 붙여주면 됩니다.
2014/01/10 - [프로그래밍/error] - deprecated conversion from string constant to 'char*'
물론 이렇게 값을 바꿀수 있습니다.
///
2014/ 9/19 추가
결론 내리자면 이 두 용어는 사용은 여러 논란이 있습니다. 포인터상수냐, 상수포인터냐의 문제는 논란이 있고 번역서 상에는 미묘한 차이가 있습니다. 어떤 번역서에서는 두 가지를 언급하지 않기도 합니다. 포인터 상수를 상수 포인터와 같은 의미로 사용하기도 합니다. 중요한 것은 이 개념에 대한 문법적인 이해라고 생각합니다.