본문 바로가기

C/C++

참조 카운팅 (Reference Counting) - 1

참조 카운팅 (Reference Counting)

 

여러 개의 객체들이 똑 같은 값을 가졌으면그 객체들로 하여금 그 값을 나타내는 하나의 데이터를 공유하게 해서 데이터의 양을 절약하는 기법

 

목적

1.     Heap 객체를 둘러싼 내부 정보를 유지하는 작업을 단순하게 하자

2.     똑 같은 값을 가지고 있는 객체들이 그 값을 하나씩 꿰어차도록 놔두는 것은 낭비

 

목적 1> 어떤 객체가 new에 의해 할당되고 난 후에는그 객체의 주인이 누구인지 따라가야 하는 것은 숙명이자 운명입니다. new한 쪽에서 bew로 만든 포인터를 해제해야겠지요하지만 프로그램이 실행되면서 이 객체의 소유권이 이 객체에서 저 객체로 왔다 갔다 할 수 있기 때문에객체의 소유권을 추적하는 일은 상당히 까다롭습니다특히 포인터를 매개변수로 넘길 때 그렇죠.

이런 참조 카운팅은 객체 소유권을 추적해야 하는 고민을 없앱니다참조 카운팅 기능을 가진 객체가 자신의 소유권을 쥐고 있기 때문이죠아무도 자신을 사용하지 않으면 스스로 자신을 소멸시킵니다일종의 가비지 콜렉션이죠

 

 목적 2> 똑 같은 값을 여러 객체가 메모리를 할당하여 쓰는 것은 낭비이자 비효율 적입니다똑같은 값을 가진 객체를 여러 번 생성하고 소멸해야 하니까요그 대신 그 값을 나타내는 데이터 하나만 공유하자는 겁니다메모리 절약은 물론속도도 빨라집니다.

 

기본부터 집고 넘어가 봅니다.

우선 똑 같은 값을 가진 객체가 여러 개 생길 수 있는 상황을 꾸며 봐야 하겠습니다.

String 클래스

class String {

public:

 

        String(const char *value = "");

        Stringoperator=(const Stringrhs);

        ...

private:

        chardata;

};

 

String abcde;

a = b = c = d = e = "Hello";

 

a부터 e까지 모두 똑 같은 값을 가졌을까요?

값을 어떻게 나타내느냐는 String 클래스를 어떻게 구현했느냐에 따라 달라지겠지만흔히 생각할 수 있는 방법은 String 객체 각각이 그 값의 사본을 하나씩 갖게 하는 것입니다아래처럼요

String.cpp

StringString::operator=(const Stringrhs)

{

       if (this == &rhsreturn *this;

 

       delete [] data;

       data = new char[strlen(rhs.data) + 1];

       strcpy(datarhs.data);

 

       return *this;

}

 

String 객체 a,b,c,d,e는 아래처럼 값을 가지고 있겟죠.

a -> Hello

b -> Hello

c -> Hello

d -> Hello

e -> Hello

 

이래저래 낭비되고 있습니다아래처럼 바꾸는게 목적입니다.

a ->

b ->

c ->                Hello

d ->

e ->

 

(모든 화살표가 하나의 'Hello'를 가르키고 있습니다. 착해야 보입니다)

“Hello” 사본 하나만 저장되고, String 객체 여러 개가 이 데이터를 공유합니다.

 

그런데문제가 있습니다객체 a에 “Hello” 이외의 값이 대입된다고 해도 “Hello”를 소멸시키면 안되죠. b~e가 유효범위를 벗어날 때 “Hello”라는 값을 가진 객체의 수는 0이 되기 때문에 그 값을 소멸시켜야 하구요.

그 값을 공유하고 있는 객체의 개수에 대한 정보가 필요하게 됩니다.

다른 말로 하면참조 카운트인거죠위의 그림은 아래와 같이 되어야 합니다.

a ->

b ->

c ->            (5) -> Hello

d ->

e ->

 

(마찬가지로, 모든 화살표가 하나의 '5'를 가르키고 있습니다.)

 

그럼 참조 카운팅 구현은 어떻게 하느냐

다음에 ….

 

<출처>

1. More Effective C++, 정보문화사, 스캇 마이어스