Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

class Geo::GeoRefCount

Base class for reference counted resources.

This class makes it possible to implement a 'poor man's garbage collection' in C++. Each class derived from this base class maintains a reference count, initially zero, incremented by the AddRef() method and decremented by the Release() method. If the reference count is zero after Release() has decremented it the object deletes itself by calling the destructor.

Reference counting is designed to be used in conjunction with factory methods. For example one might define the class Foo which can be reference counted:

Code Block
class Foo : public GeoRefCount
{
public:
    static Foo* CreateFoo()
    {
        Foo* myFoo = GEO_NEW(Foo);      // Ref count will be 0
        if (!myFoo)     return 0;
        if (!myFoo->Setup(...))
        {
            // failed!
            GEO_DELETE(Foo, myFoo);
            return 0;
        }
        // success!
        myFoo->AddRef();    // ref count -> 1
        return myFoo;
    }
protected:
    Foo()
    {
        // The constructor is protected so that Foo has to 
        // be allocated via the factory method. 
    }
};
To create a new instance of Foo, non-friends are forced to use the CreateFoo() factory method which leaves the reference count as one. Once the instance is finished with the Release() method is called. For example:
Code Block
...
Foo*    my_foo = Foo::CreateFoo();
SomeExcitingFunction(my_foo);
my_foo->Release();
...
Suppose the SomeExcitingFunction() function wishes to keep the pointer to my_foo around for future use. In this case it should AddRef() it for as long as it wishes until it wants to Release() it.

The rule of thumb for reference counting is if you AddRef() or Create...() it, you must at some point Release() it.

GeoRefCount also allows the same class to be used in a non-ref-counted scenario. In this case you allow NEW and DELETE as usual, but once AddRef is called you must use Release. For instance, DirectGeoMeshLoader uses this strategy to return GeoMeshes which are "owned" by the caller, rather than just "existing" somewhere.

Variables

NameDescription
s32 m_RefCount

The reference count, once it reaches zero the object deletes itself.

Functions

NameDescription
~GeoRefCount()

Virtual destructor required to make sure that the concrete class destructor gets called.

AddRef()

Increments the reference count and return new value.

GeoRefCount()

Default constructor. The reference count is initially zero.

Release()

Decrements the reference count, deleting the object if it reaches zero.


Anchor
a9af10d210d8dee5f975c23c0be4c7b63
a9af10d210d8dee5f975c23c0be4c7b63

virtual Geo::GeoRefCount::~GeoRefCount

...

public: virtual ~GeoRefCount()

...

Virtual destructor required to make sure that the concrete class destructor gets called.


Anchor
a8d0095fb588cfcd18249fa0e48cc53d3
a8d0095fb588cfcd18249fa0e48cc53d3

s32 Geo::GeoRefCount::AddRef

...

public: s32 AddRef()

...

Increments the reference count and return new value.

Returns

New value of reference count.


Anchor
a99c8112957fc10e563e95dc29cdeb08a
a99c8112957fc10e563e95dc29cdeb08a

Geo::GeoRefCount::GeoRefCount

...

public: GeoRefCount()

...

Default constructor. The reference count is initially zero.


Anchor
a1c645a8988542a364c082b58bd2f8e46
a1c645a8988542a364c082b58bd2f8e46

s32 Geo::GeoRefCount::Release

...

public: s32 Release()

...

Decrements the reference count, deleting the object if it reaches zero.

Returns

Returns reference count after decrement. 0 if deleted.