C++ 句柄类的原理以及设计

句柄类存在的意义是为了弥补将派生类对象赋给基类对象时发生的切片效应。例如下面的程序:
multimap<Base> basket;
Base base;
Derived derive;
basket.insert(base);	//ok,add copy of base;
basket.insert(derive);	//ok,but derive sliced down to its base part.

也就是说在把派生类的对象赋值给基类的时候,会发生切片效益,派生类的非基类部分会被切掉,那么就失去了本身的意义。为了解决这个问题我们可以
使用基于基类的指针或者引用,但是设计到指针问题的话就涉及到资源不使用后的释放问题。这就引出了句柄类,它类似智能指针,可以在我们复制资源
的时候不用去担心内存泄露的问题。整个程序的设计如下所示:
//Base.h
#pragma once
class Base
{
public:
	Base(void);
	virtual ~Base(void);
	virtual Base* clone() const;
	virtual void fine() const;
private:
	int mb;
};

//Base.cpp
#include "Base.h"
#include <iostream>
using namespace std;


Base::Base(void):mb(12)
{
}


Base::~Base(void)
{
}


Base* Base::clone() const
{
	return new Base(*this);
}


void Base::fine() const
{
	cout<<"Base fine function"<<endl;
}

//Derive.h
#pragma once
#include "base.h"
class Derive :
	public Base
{
public:
	Derive(void);
	virtual ~Derive(void);
	virtual Derive* clone() const;
	virtual void fine() const;
private:
	int md;
};

//Derive.cpp
#include "Derive.h"
#include <iostream>
using namespace std;


Derive::Derive(void):Base(),md(13)
{
}


Derive::~Derive(void)
{


}


Derive* Derive::clone() const
{
	return new Derive(*this);
}


void Derive::fine() const
{
	cout<<"Derive fine function"<<endl;
}

//Handles.h 
#pragma once
#include "Base.h"
#include <iostream>
class Handles
{
public:
	Handles(void);
	Handles(const Base&);
	Handles(const Handles& h);
	~Handles(void);


	const Base* operator->()const;
	const Base& operator*()const;
	Handles& operator=(const Handles&);


	
private:
	Base*	p;
	std::size_t*	use;
	void dec_use()
	{
		if(--*use == 0)
		{
			delete p;
			delete use;
			std::cout<<"delete resource"<<std::endl;
		}
	}


};

//Handle.cpp 
#include "Handles.h"


Handles::Handles(void):p(NULL),use(new size_t(1))
{
}


Handles::Handles(const Handles& h):p(h.p),use(h.use)
{
	++*use;
}


Handles::Handles(const Base& item):p(item.clone()),use(new std::size_t(1))
{
}
const Base& Handles::operator*()const
{
		if(p) 
			return *p;
		else
			throw std::logic_error("unbounded Handles");
}


const Base* Handles::operator->()const
{
		if(p) 
			return p;
		else
			throw std::logic_error("unbounded Handles");
}


Handles& Handles::operator=(const Handles& h)
{
	++*h.use;
	dec_use();
	p = h.p;
	use = h.use;
	return *this;
}


Handles::~Handles()
{
	dec_use();
}

//main.cpp
#include <iostream>
#include "Handles.h"
#include "Derive.h"
#include <vector>
using namespace std;
void main()
{
	vector<Handles> mb;
	Base b;
	Derive d;
	mb.push_back(Handles(b));
	mb.push_back(Handles(d));
	mb[0]->fine();
	mb[1]->fine();
	system("pause");
} 



郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。