728x90
반응형
포인터를 사용하면 잠재적으로 많은 양의 데이터를 저렴한 비용으로 전달할 수 있다. 데이터를 복사하는 대신 해당 주소를 포인터 값으로 전달하면 된다. 포인터의 유형은 포인터를 통해 데이터에 수행할 수 있는 작업을 결정한다. 포인터를 사용하는 것은 다음과 같은 몇 가지 면에서 객체 이름을 사용하는 것과 다르다.
- 다른 구문을 사용한다.
예를 들어 obj 대신 p->m을 사용한다. - 포인터가 다른 시간에 다른 객체를 가리키도록 할 수 있다.
- 객체를 직접 사용할 때보다 포인터를 사용할 때 더 주의해야 한다.
nullptr이거나 기대하지 않은 객체를 가리킬 수 있다.
이러한 차이점은 성가실 수 있다. 예를 들어, 일부 프로그래머는 f(&x)가 f(x)에 비해 깔끔하지 못하다고 생각한다. 게다가 다양한 값으로 포인터 변수를 관리하고 nullptr 가능성으로부터 코드를 보호하는 것은 상당히 부담스러운 일이다. 마지막으로 +라고 하는 연산자를 오버 로드하고 싶을 때 &x + &y 대신 x+y를 쓰고 싶어 한다. 이러한 문제를 해결할 수 있는 것이 참조다.
포인터와 마찬가지로 참조는 객체의 별칭이며 일반적으로 객체의 기계 주소를 유지하기 위해 구현되며 포인터에 비해 성능 오버헤드를 부과하지 않지만 다음과 같은 점에서 포인터와 다른다.
- 객체 이름과 정확히 동일한 구문으로 참조에 액세스 한다.
- 참조는 항상 초기화된 객체를 참조한다.
- null reference가 없으며 참조가 객체를 참조한다고 가정할 수 있다.
참조는 객체의 대체 이름인 별칭이다. 참조의 주요 용도는 일반적으로 함수 및 오버 로드된 연산자에 대한 인수 및 반환 값을 지정하는 것이다.
template<class T>
class vector {
T∗ elem;
// ...
public:
T& operator[](int i) { return elem[i]; } // return reference to element
const T& operator[](int i) const { return elem[i]; } // return reference to const element
void push_back(const T& a); // pass element to be added by reference
// ...
};
void f(const vector<double>& v)
{
double d1 = v[1]; // copy the value of the double referred to by v.operator[](1) into d1
v[2] = 7; // place 7 in the double referred to by the result of v.operator[](2)
v.push_back(d1); // give push_back() a reference to d1 to wor k with
}
참조로 함수 인수를 전달하는 아이디어는 고급 프로그래밍 언어만큼 오래되었다. (포트란의 첫 번째 버전에서 이를 사용했다.)
lvalue/rvalue 및 const/non-const 구분을 반영하기 위해 세 가지 종류의 참조가 있다.
- lvalue 참조 : 값을 변경하려는 객체 참조
- const 참조 : 값을 변경하고 싶지 않은 객체 참조 (예 : 상수)
- rvalue 참조 : 값을 얻은 후에 보존할 필요가 없는 객체 참조 (예 : 임시)
이를 총칭하여 참조라고 한다. 처음 두 개는 모두 lvalue 참조라고 한다.
728x90
반응형
'Program Language > C & C++' 카테고리의 다른 글
[C++] rvalue 참조 (0) | 2021.12.29 |
---|---|
[C++] lvalue 참조 (0) | 2021.12.29 |
[C++] pointer & 소유권 (0) | 2021.12.29 |
[C++] Pointer & const (0) | 2021.12.29 |
[C++] 포인터(Pointer) (0) | 2021.12.23 |