zoukankan      html  css  js  c++  java
  • [C/C++] Very very good !!! 句柄类

    方案二
       为了避免上面方案中每个使用指针的类自己去控制引用计数,可以用一个类把指针封装起来。封装好后,这个类对象可以出现在用户类使用指针的任何地方,表现为一个指针的行为。我们可以像指针一样使用它,而不用担心普通成员指针所带来的问题,我们把这样的类叫句柄类。在封装句柄类时,需要申请一个动态分配的引用计数空间,指针与引用计数分开存储。实现示例如下: 
    #include <iostream>
    #include <string>
    #include <cstring>
    #include <cstdlib>
    #include <cstdio>
    #include <cmath>
    #include <vector>
    #include <stack>
    #include <deque>
    #include <queue>
    #include <bitset>
    #include <list>
    #include <map>
    #include <set>
    #include <iterator>
    #include <algorithm>
    #include <functional>
    #include <utility>
    #include <sstream>
    #include <climits>
    #include <cassert>
    #include <stdexcept>
    #define BUG puts("here!!!");
    
    using namespace std;
    class Stub {
    public :
    	void show() { printf("Stub showed!"); }
    	~Stub() {
    		cout << "Stub : Destructor" << endl;
    	}
    };
    template <typename T> 
    class Handle {
    public :
    	Handle(T *p = 0) : ptr(p), pUse(new size_t(1)) {}
    	Handle(const T& src) : ptr(src.ptr), pUse(src.pUse) { *pUse++; }
    	Handle& operator= (const Handle &rhs) {
    		++*rhs.pUse;
    		decrUse();
    		ptr = rhs.ptr;
    		pUse = rhs.pUse;
    		return *this;
    	}
    	T *operator-> () {
    		if(ptr) return ptr;
    		throw std::runtime_error("NULL point");
    	}
    	const T *operator-> () const {
    		if(ptr) return ptr;
    		throw std::runtime_error("NULL point");
    	}
    	T &operator* () {
    		if(ptr) return *ptr;
    		throw std::runtime_error("NULL point");
    	}
    	const T &operator* () const {
    		if(ptr) return *ptr;
    		throw std::runtime_error("NULL point");
    	}
    	~Handle() {
    		decrUse();
    		std::cout << "Handle destructor" << endl;
    	}
    private :
    	void decrUse() {
    		--(*pUse);  // 
    		if(*pUse == 0) {
    			delete ptr;
    			delete pUse;
    		}
    	}
    
    	T *ptr;
    	size_t *pUse;
    };
    int main() {
    	try {
    		Handle<Stub> t;
    		t->show();
    	} catch (const exception& err) {
    		cout << err.what() << endl;
    	}
    	BUG
    	Handle<Stub> t1(new Stub);
    	Handle<Stub> t2(t1);
            (*t2).show();
    	
    	return 0;
    }

  • 相关阅读:
    爬虫|如何在Pycharm中调试JS代码
    nexus 6p 输入8.1和获取root权限
    年近30的我,离开了北京,回家做个老百姓,等待那一刻的发生!
    Azure认知服务的实际应用-资讯采集推送
    C#类库推荐 拼多多.Net SDK,开源免费!
    [翻译]EntityFramework Core 2.2 发布
    4-如何学习和解决问题
    3-WIN10系统及开发工具支持
    2-选择学习的目标和方向
    1-编程的基本条件和起步
  • 原文地址:https://www.cnblogs.com/robbychan/p/3786725.html
Copyright © 2011-2022 走看看