禁止或强制使用堆分配---《C++必知必会》 条款34
有时候,指明一些特定类的对象不应该被分配到堆(heap)上是个好主意。通常这是为了确保该对象的析构函数一定会得到调用。维护对象本身(body object)的引用计数的句柄对象(handle object)就属于这种对象。具有自动存储区的类的局部对象,其析构函数会被自动调用(exit 或abort发生的非正常的程序终止情况出外),具有静态存储区的对象依然(abort除外),而堆分配的对象则必须被显示的销毁。
指明对象不应该被分配到堆上的方式之一,是将其内存分配定义为不合法:
#include<iostream>
class NoHeap{
protected:
void * operator new(size_t){return 0;}
//size_t 参数将被自动初始化为NoHeap对象的大小(以字节为单位)。
void operator delete(void *){}
//void * 参数被编译器自动设置为"将被delete的那个对象地址"
private:
void * operator new[](size_t){return 0;}
void operator delete[](void *);
};
class OnHeap{
private:
~OnHeap(){};
public:
void destory(){ delete this;}
//同时要提供一个共有的销毁对象的方法(例如:destroy),否则创建的对象将无从销毁
}; int main(int argc, char* argv[])
{
NoHeap ok; NoHeap * nh = new NoHeap;//错误!
delete nh;//错误!
OnHeap oh1; //错误!隐式调用私有析构函数 OnHeap *oh2 = new OnHeap; //正确!
oh2->destory(); //正确!
return 0;
}
任何在堆上分配一个NoHeap对象的习惯性尝试,都将会导致编译期错误。
之所以给出operator new 和 operator delete的定义(和声明),是因为在一些平台上他们可能会被构造函数和析构函数隐式调用。出于同样原因,我们将其声明为protected,因为它们可能会被派生类的构造函数和析构函数隐式调用。如果NoHeap不做基类,那么这两个函数也可以声明为private的。
同时,还要注意阻止在堆上分配NoHeap对象的数组。在这种情况下,只要将 array new 和 array delete声明为private且不予以定义即可,类似于禁止复制操作的方式。
当然,在某些场合下,我们可能鼓励而非阻止使用堆分配,为此,只需将析构函数声明为private即可。当对象的名字离开作用域时,任何一个声明或静态OnHeap对象的尝试,都将会导致一个隐式析构函数的调用,将发生错误。
禁止或强制使用堆分配---《C++必知必会》 条款34的更多相关文章
- 《C++必知必会》学习笔记
转载:http://dsqiu.iteye.com/blog/1734640 条款一 数据抽象 抽象数据设计遵循步骤:(1)为类型取一个描述性的名字.(2)列出类型所能执行的操作,不要忘了初始化(构造 ...
- SQL 必知必会
本文介绍基本的 SQL 语句,包括查询.过滤.排序.分组.联结.视图.插入数据.创建操纵表等.入门系列,不足颇多,望诸君指点. 注意本文某些例子只能在特定的DBMS中实现(有的已标明,有的未标明),不 ...
- 《MySQL必知必会》整理
目录 第1章 了解数据库 1.1 数据库基础 1.1.1 什么是数据库 1.1.2 表 1.1.3 列和数据类型 1.1.4 行 1.1.5 主键 1.2 什么是SQL 第2章 MySQL简介 2.1 ...
- 读《MySQL必知必会》我学到了什么?
前言 最近在写项目的时候发现自己的SQL基本功有些薄弱,遂上知乎查询MYSQL关键字,期望得到某些高赞答案的指点,于是乎发现了 https://www.zhihu.com/question/34840 ...
- 【MySQL 基础】MySQL必知必会
MySQL必知必会 简介 <MySQL必知必会>的学习笔记和总结. 书籍链接 了解SQL 数据库基础 什么是数据库 数据库(database):保存有组织的数据的容器(通常是一个文 件或一 ...
- 脑残式网络编程入门(三):HTTP协议必知必会的一些知识
本文原作者:“竹千代”,原文由“玉刚说”写作平台提供写作赞助,原文版权归“玉刚说”微信公众号所有,即时通讯网收录时有改动. 1.前言 无论是即时通讯应用还是传统的信息系统,Http协议都是我们最常打交 ...
- 第5节:Java基础 - 必知必会(下)
第5节:Java基础 - 必知必会(下) 本小节是Java基础篇章的第三小节,主要讲述Java中的Exception与Error,JIT编译器以及值传递与引用传递的知识点. 一.Java中的Excep ...
- MySQL必知必会1-20章读书笔记
MySQL备忘 目录 目录 使用MySQL 检索数据 排序检索数据 过滤数据 数据过滤 用通配符进行过滤 用正则表达式进行搜索 创建计算字段 使用数据处理函数 数值处理函数 汇总数据 分组数据 使用子 ...
- 必知必会之 Java
必知必会之 Java 目录 不定期更新中-- 基础知识 数据计量单位 面向对象三大特性 基础数据类型 注释格式 访问修饰符 运算符 算数运算符 关系运算符 位运算符 逻辑运算符 赋值运算符 三目表达式 ...
随机推荐
- JavaScript------去掉Array中重复值
转载: http://blog.csdn.net/teresa502/article/details/7926796 代码: // 删除数组中重复数据 function removeDuplElem( ...
- day04<Java语言基础+>
Java语言基础(循环结构概述和for语句的格式及其使用) Java语言基础(循环结构for语句的练习之获取数据) Java语言基础(循环结构for语句的练习之求和思想) Java语言基础(循环结构f ...
- org.apache.ibatis.builder.IncompleteElementException: Could not find parameter map com.hyzn.historicalRecord.dao.ITB_HISTORYLOGDAO.TB_HISTORYLOGResultMap
用了很久的myBatis,忽然出现这个错误,感觉配置什么的都是正确的,错误如下: org.apache.ibatis.builder.IncompleteElementException: Could ...
- strip() 、lstrip() 、rstrip()
strip() 用于移除字符串开头和结尾的空格或换行符,如果指定参数,则表示移除指定的字符lstrip() 用于移除字符串开头的空格或换行符,如果指定参数,则表示移除指定的字符rstrip() 用于移 ...
- 基于Cocos2d-x学习OpenGL ES 2.0系列——初识MVP(3)
在上一篇文章中,我在介绍vertex shader的时候挖了一个坑:CC_MVPMatrix.它其实是一个uniform,每一个Cocos2d-x预定义的shader都包含有这个uniform,但是如 ...
- poj_1442 Treap
Treap是一种动态平衡二叉树结构,具有期望的O(log2n)的复杂度.适用于动态区间数据的查询.更改.维护等操作. 题目大意 一组数从前向后插入队列中,插入的过程中会有查询,查询当前队列中的第k小的 ...
- Sass-学习笔记【基础篇】
最下边附结构图 在线编辑器网址如下:http://sassmeister.com/ 注意编写的时候,符号千万别用了中文的:.:.....之类的,会报错,Sass也转换不成css. less和sass ...
- JS-cookie封装
智能社学习笔记 <script type="text/javascript"> /*****设置cookie*****/ function setCookie(name ...
- WEB安全第四篇--与数据库的亲密接触:SQL注入攻击
零.前言 最近做专心web安全有一段时间了,但是目测后面的活会有些复杂,涉及到更多的中间件.底层安全.漏洞研究与安全建设等越来越复杂的东东,所以在这里想写一个系列关于web安全基础以及一些讨巧的pay ...
- 主流品牌服务器(Dell、HP、IBM)远程管理卡IP配置参考
版权声明:个人网络收集整理,欢迎转载! https://blog.csdn.net/niufenger/article/details/80737878 ※Dell服务器iDRAC IP配置 ※HP服 ...