본문 바로가기
프로그래밍 언어/C++

[C++] 스마트 포인터(Smart Pointer) 원리

by 까망 하르방 2025. 3. 12.
반응형

스마트 포인터(Smart Pointer)란?

다른 타입의 포인터 역할을 하는 "객체"

#include <iostream>

class Harbang
{
	int color;
public:
	~Harbang() { printf("~Harbang"); }
	void foo() { std::printf("foo"); }
};

class Ptr
{
	Harbang* obj;
public:
	explicit Ptr(Harbang* p = nullptr) : obj{ p } {}

	~Ptr() { delete obj; }

	Harbang* operator->() { return obj; }
	Harbang& operator*() { return *obj; } // 임시 객체 생성 막기 위해 Reference 반환
};

int main()
{
	Ptr p(new Harbang);  // 타입 Ptr 객체

	p->foo();    // 1) ?? -> ok 
	(*p).foo();  // 2) ?? -> ok
}



Q) 「Ptr p」는 포인터가 아니라 객체이다.
 「p->foo()」 「(*p).foo()」 와 같이 포인터 변수처럼 활용하는 것은 어떻게 가능할까?


A) 「->」 「*」 연산자 재정의
 Ptr 객체가 Harbang * 역할을 수행하고 있기 때문
 즉, Harbang* 보관할 수 있는 멤버 데이터를 가진다.

① 「p->foo()」 = (p.operator->())->foo()
② 「(*p).foo()」 = (p.operator*()).foo()

「 * 」 연산자는 임시 객체 생성을 막기 위해 Reference 반환

 

📌 [C++] 연산자 재정의 (Operator Overloading)

 

[C++] 연산자 재정의 (Operator Overloading)

연산자 재정의 (Operator Overloading)사용자 정의 타입에서 +, - 등 연산자 사용할 수 있는 문법class Point{ int x = 0; int y = 0;public: Point() = default; Point(int x, int y) : x{ x }, y{ y } {}};int main(){ Point p1{ 1, 1 }; Point

zoosso.tistory.com


Q) 일반적인 Point 사용하지 않고 Smart Pointer 사용하는 이유


A) 스마트 포인터는 객체이기 때에
 생성/복사/대입/소멸 과정에서 추가 작업 수행 가능 
 ex) 소멸자 통해 쉽게 delete

#include <iostream>

class Harbang
{
	int color;
public:
	~Harbang() { printf("~Harbang"); }
	void foo() { printf("foo"); }
};

int main()
{
   Harbang* p = new Harbang; // 사용 후 사용자가 delete 처리 필요
}



[예시] 다양한 타입을 받기 위한 Template 적용

#include <iostream>

template<typename T>
class Ptr
{
	T* obj;
public:
	explicit Ptr(T* p = nullptr) : obj{ p } {}

	~Ptr() { delete obj; }

	T* operator->() { return obj; }
	T& operator*() { return *obj; }
};

int main()
{
	Ptr<int> p(new int);
	
	*p = 10;
	
	printf("%d", *p);
}



std::shared_ptr

• C++ 표준에서 제공하는 스마트 포인터
• <memory> 헤더

#include <iostream>
#include <memory>

class Harbang
{
public:
	~Harbang() { printf("~Harbang()\n"); }
	void foo() { printf("foo\n"); }
};

int main()
{
	// std::shared_ptr<Car> sp1 = new Car; // error

	std::shared_ptr<Harbang> sp2( new Harbang );  // ok

	std::shared_ptr<Harbang> sp3{ new Harbang };  // ok
	sp2->foo();
}



smart point에서 생성자가 explict 되어 있을 것이기에
[std::shared_ptr<Car> sp1 = new Car] 와 같은 대입 초기화는 되지 않는다.

 

📌 [C++] explicit 키워드

 

[C++] explicit 키워드

explicit 키워드는 묵시적 형변환을 할 수 없게 만들고 명시적인 형변환만 가능하도록 만드는 것이다. 주로 생성자에 explict를 활용한다. why? 의도하지 않은 오류를 방지하기 위함이다. = 원하지 않

zoosso.tistory.com

반응형

댓글