大胖的部落格

Just a note

  C++博客 :: 首页 :: 新随笔 :: 联系 :: 聚合  :: 管理 ::
  112 随笔 :: 0 文章 :: 3 评论 :: 0 Trackbacks
1. 非侵入式:static map<unsigned int, int>,key是对象地址,value是counter。
2. 非侵入式:构造函数new一个int作为counter,拷贝构造函数和赋值操作符中传递该counter。
3. 侵入式:定义一个Count基类自带counter,所有对象继承与Count基类,counter在对象中。
方法2无法重载 operator = (T *t),因为无法从参数中获得t的counter信息。

Code1: 用static map作为counter
#include <stdio.h>
#include 
<map>

using namespace std;


class A
{
public:
    A()
    {
        printf(
"\nA Construct\n");
    }
    
    
~A()
    {
        printf(
"\nA Destruct\n");
    }
};

class B
{
public:
    B()
    {
        printf(
"\nB Construct\n");
    }
    
    
~B()
    {
        printf(
"\nB Destruct\n");
    }
};

template 
<typename T>
class SmartPtr
{
public:
    SmartPtr(T 
*t)
    {
        Pointee 
= t;
        
        map
<unsigned intint>::iterator it = CountMap.find((unsigned int)t);
        
if(it != CountMap.end())
            
++(it->second);
        
else
            CountMap[(unsigned 
int)Pointee] = 1;
    }
    
    SmartPtr(
const SmartPtr &sp)
    {
        Pointee 
= sp.Pointee;
        
        map
<unsigned intint>::iterator it = CountMap.find((unsigned int)Pointee);
        
if(it != CountMap.end())
            
++(it->second);
        
else
            CountMap[(unsigned 
int)Pointee] = 1;
    }
    
    SmartPtr
& operator = (const SmartPtr &sp)
    {
        
if(NULL != Pointee)
        {
            
--CountMap[(unsigned int)Pointee];
            
if(CountMap[(unsigned int)Pointee] == 0)
            {
                CountMap.erase((unsigned 
int)Pointee);
                delete Pointee;
                Pointee 
= NULL;
            }
        }
        
        Pointee 
= sp.Pointee;
        
        map
<unsigned intint>::iterator it = CountMap.find((unsigned int)Pointee);
        
if(it != CountMap.end())
            
++(it->second);
        
else
            CountMap[(unsigned 
int)Pointee] = 1;
        
        
return *this;
    }
    
    SmartPtr
& operator = (T *t)
    {
        
if(NULL != Pointee)
        {
            
--CountMap[(unsigned int)Pointee];
            
if(CountMap[(unsigned int)Pointee] == 0)
            {
                CountMap.erase((unsigned 
int)Pointee);
                delete Pointee;
                Pointee 
= NULL;
            }
        }
        
        Pointee 
= t;
        
        map
<unsigned intint>::iterator it = CountMap.find((unsigned int)Pointee);
        
if(it != CountMap.end())
            
++(it->second);
        
else
            CountMap[(unsigned 
int)Pointee] = 1;
        
        
return *this;
    }
    
    
~SmartPtr()
    {
        
if(NULL != Pointee)
        {
            
--CountMap[(unsigned int)Pointee];
            
if(CountMap[(unsigned int)Pointee] == 0)
            {
                CountMap.erase((unsigned 
int)Pointee);
                delete Pointee;
                Pointee 
= NULL;
            }
        }
    }
private:
    T 
*Pointee;
    
static map<unsigned intint> CountMap;
    SmartPtr();
};

template 
<typename T> 
map
<unsigned intint> SmartPtr<T>::CountMap;

int main()
{
    A 
*objA1 = new A();
    A 
*objA2 = new A();
    A 
*objA3 = new A();
    B 
*objB1 = new B();
    B 
*objB2 = new B();
    B 
*objB3 = new B();
    
    SmartPtr
<A> sPtrA1(objA1);
    SmartPtr
<A> sPtrA2(objA2);
    sPtrA1 
= sPtrA2;
    sPtrA1 
= objA3;
    sPtrA2 
= objA3;
    
    SmartPtr
<B> sPtrB1(objB1);
    SmartPtr
<B> sPtrB2(objB2);
    sPtrB1 
= sPtrB2;
    sPtrB1 
= objB3;
    sPtrB2 
= objB3;
    
return 0;
}

Code2: 用new int作为counter
#include <stdio.h>

class A
{
public:
    A()
    {
        printf(
"\nA Construct\n");
    }
    
    
~A()
    {
        printf(
"\nA Destruct\n");
    }
};

class B
{
public:
    B()
    {
        printf(
"\nB Construct\n");
    }
    
    
~B()
    {
        printf(
"\nB Destruct\n");
    }
};

template 
<typename T>
class SmartPtr
{
public:
    SmartPtr(T 
*t)
    {
        Pointee 
= t;

        Count 
= new int(0);
        
++(*Count);
    }
    
    SmartPtr(
const SmartPtr &sp)
    {
        Pointee 
= sp.Pointee;
        Count 
= sp.Count;
        
++(*Count);
    }
    
    SmartPtr
& operator = (const SmartPtr &sp)
    {
        
if(NULL != Pointee)
            
--(*Count);
        
if(*Count == 0)
            delete Pointee;
        
        Pointee 
= sp.Pointee;
        Count 
= sp.Count;
        
++(*Count);
        
        
return *this;
    }
    
    
// Cannot work well.
    
// Should not public this method.
    SmartPtr& operator = (T *t)
    {
        
if(NULL != Pointee)
            
--(*Count);
        
if(*Count == 0)
        {
            delete Pointee;
            delete Count;
        }
        Pointee 
= t;
        
// Cannot get the counter on t.
        Count = new int(0);
        
++(*Count);
        
        
return *this;
    }
    
    
~SmartPtr()
    {
        
if(NULL != Pointee)
            
--(*Count);
        
if(*Count == 0)
        {
            delete Pointee;
            Pointee 
= NULL;
        }
        delete Count;
    }
private:
    T 
*Pointee;
    
int *Count;
    SmartPtr();
};

int main()
{
    A 
*obj1 = new A();
    A 
*obj2 = new A();
    A 
*obj3 = new A();
    B 
*objB1 = new B();
    B 
*objB2 = new B();
    B 
*objB3 = new B();
    
    SmartPtr
<A> sPtr1(obj1);
    SmartPtr
<A> sPtr2(obj2);
    sPtr1 
= sPtr2;
    sPtr1 
= obj3;
    
// Comment out since SmartPtr cannot get the existing counter on obj3.
    
//sPtr2 = obj3;
    
    SmartPtr
<B> sPtrB1(objB1);
    SmartPtr
<B> sPtrB2(objB2);
    sPtrB1 
= sPtrB2;
    sPtrB1 
= objB3;
    
// Comment out since SmartPtr cannot get the existing counter on objB3.
    
//sPtrB2 = objB3;
    return 0;
}

Code3: 对象继承与Count基类,counter在对象内
#include <stdio.h>

class ReferenceCount
{
public:
    
virtual ~ReferenceCount(){};
    
int Count;
protected:
    ReferenceCount():Count(
0){};
};

class Intrusive: public ReferenceCount
{
public:
    Intrusive()
    {
        printf(
"\nInstrusive Construct\n");
    }
    
    
~Intrusive()
    {
        printf(
"\nInstrusive Destruct\n");
    }
};


class B: public ReferenceCount
{
public:
    B()
    {
        printf(
"\nB Construct\n");
    }
    
    
~B()
    {
        printf(
"\nB Destruct\n");
    }
};

template 
<typename T>
class SmartPtrIntrusive
{
public:
    SmartPtrIntrusive(T 
*t)
    {
        Pointee 
= t;
        
++Pointee->Count;
    }
    
    SmartPtrIntrusive(
const SmartPtrIntrusive &sp)
    {
        Pointee 
= sp.Pointee;
        
++Pointee->Count;
    }
    
    SmartPtrIntrusive
& operator = (const SmartPtrIntrusive &sp)
    {
        
if(NULL != Pointee)
            
--Pointee->Count;
        
if(Pointee->Count == 0)
        {
            delete Pointee;
            Pointee 
= NULL;
        }
        
        Pointee 
= sp.Pointee;
        
++Pointee->Count;
        
        
return *this;
    }
    
    SmartPtrIntrusive
& operator = (T *t)
    {
        
if(NULL != Pointee)
            
--Pointee->Count;
        
if(Pointee->Count == 0)
        {
            delete Pointee;
            Pointee 
= NULL;
        }

        Pointee 
= t;
        
++Pointee->Count;
        
        
return *this;
    }
    
    
~SmartPtrIntrusive()
    {
        
if(NULL != Pointee)
            
--Pointee->Count;
        
if(Pointee->Count == 0)
        {
            delete Pointee;
            Pointee 
= NULL;
        }
    }
private:
    T 
*Pointee;
    SmartPtrIntrusive();
};

int main()
{
    Intrusive 
*obj1 = new Intrusive();
    Intrusive 
*obj2 = new Intrusive();
    Intrusive 
*obj3 = new Intrusive();
    B 
*objB1 = new B();
    B 
*objB2 = new B();
    B 
*objB3 = new B();
    SmartPtrIntrusive
<Intrusive> sPtr1(obj1);
    SmartPtrIntrusive
<Intrusive> sPtr2(obj2);
    sPtr1 
= sPtr2;
    sPtr1 
= obj3;
    sPtr2 
= obj3;
    
    SmartPtrIntrusive
<B> sPtrB1(objB1);
    SmartPtrIntrusive
<B> sPtrB2(objB2);
    sPtrB1 
= sPtrB2;
    sPtrB1 
= objB3;
    sPtrB2 
= objB3;
    
return 0;
}
posted on 2011-08-10 21:40 大胖 阅读(559) 评论(0)  编辑 收藏 引用 所属分类: C++

只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   博问   Chat2DB   管理