如果容器中包含了通过new操作创建的指针,切记在容器对象析构前将指针delete掉

如果容器中包含了通过new操作创建的指针,切记在容器对象析构前将指针delete掉

在STL中容器是智能的,可以在容器销毁时自动调用容器里对象的析构函数来销毁容器存储的对象。

STL的容器虽然比较智能,但是没有智能到可以自动销毁new出来的指针对象。

所以在使用STL中的容器时,如果保存的是mew出来的对象的指针。如果在容器销毁之前没有把new出来的对象释放,会造成内存泄露。

解决方法版本一:

这种手工释放容器里new的对象不太可靠,菲异常安全的。如果在delete的时候爆出异常,那么还是会引起内存泄露。

解决方法二:

使用函数对象的方式,可以保证对象的安全销毁完,虽然在调用时需要指明函数对象类型,实现了适配器作用

但是这种方法需要公有继承,有个特殊情况,就是STL的string。

string是没有虚析构函数的,所以在作为基类时,在这个对象使用完析构时,会找不到对应的析构函数,这时的行为是未知的。

解决方法三:

把模板化放在类里面,重载()操作符前,由编译器自动判断调用者的类型,这样就可以避免公有继承这一步操作,也就实现了通用。但是却丢弃了可适配的能力。

最优的解决方法:

使用boost里的shared_ptr智能指针,通过其的自动计算引用计数的实现来,在使用STL容器保存new出来的对象指针时,超出作用域范围自动销毁智能指针里的对象,实现安全可靠高效的解决内存泄露方案。

总的来说,在使用STL容器存储new出来的对象的指针时,需要注意对象的析构销毁步骤。这一步是需要我们自己来管理的。

原文地址:https://www.cnblogs.com/liangjf/p/10166039.html

时间: 2024-11-03 12:58:28

如果容器中包含了通过new操作创建的指针,切记在容器对象析构前将指针delete掉的相关文章

Effective STL 第7条:如果容器中包含了通过new操作创建的指针,切记在容器对象析构前将指针delete掉

STL中的容器相当"聪明",它们提供了迭代器,以便进行向后和向前的遍历(通过begin.end.rbegin等):它们告诉你所包含的元素类型(通过它们的value_type类型定义):在插入和删除的过程中,它们自己进行必要的内存管理:它们报告自己有多少对象,最多能容纳多少对象(分别通过size和max_size):当然,当它们自身被析构时,它们自动析构所包含的每个对象. 有了这么"聪明"的容器,许多程序员不再考虑自己做善后清理工作.更糟糕的是,他们认为,容器会考虑为

js数组容器中包含的属性和方法概述

1..length----获取数组长度: var arr = [1,2,3,4,5]; console.log(arr.length) //5 2.shift()----删除原数组第一项,并返回删除元素的值:如果数组为空则返回undefined,直接在元数组上修改: var arr= [1,2,3,4,5]; var result = arr.shift(); console.log(arr) //[2,3,4,5] console.log(result) //1 3.unshift()----

Docker容器中的数据管理--RHEL7.3

容器中数据管理主要分为两种方式:数据卷 和 数据卷容器 数据卷 数据卷是一个可供容器使用的特殊目录,它绕过文件系统,类似于Linux下对目录执行mount操作 创建一个数据卷 在容器内创建数据卷挂载到/volume目录下,相当于容器间的共享目录: docker run -dti -v /volume1 --name test1 centos:ifconfig /bin/bash 将宿主机目录挂载到容器作为数据卷: docker run -dti -v /test:volume2:ro --nam

spring在IoC容器中装配Bean详解

1.Spring配置概述 1.1.概述 Spring容器从xml配置.java注解.spring注解中读取bean配置信息,形成bean定义注册表: 根据bean定义注册表实例化bean: 将bean实例放入bean缓存池: 应用程序使用bean. 1.2.基于xml的配置 (1)xml文件概述 xmlns------默认命名空间 xmlns:xsi-------标准命名空间,用于指定自定义命名空间的schema文件 xmlns:xxx="aaaaa"-------自定义命名空间,xx

在 docker 容器中捕获信号

原文:在 docker 容器中捕获信号 我们可能都使用过 docker stop 命令来停止正在运行的容器,有时可能会使用 docker kill 命令强行关闭容器或者把某个信号传递给容器中的进程.这些操作的本质都是通过从主机向容器发送信号实现主机与容器中程序的交互.比如我们可以向容器中的应用发送一个重新加载信号,容器中的应用程序在接到信号后执行相应的处理程序完成重新加载配置文件的任务.本文将介绍在 docker 容器中捕获信号的基本知识. 信号(linux) 信号是一种进程间通信的形式.一个信

Docker拷贝宿主机与容器中的文件

如果我们需要将宿主机文件拷贝到容器内可以使用 docker cp 命令,也可以将文件从容器内拷贝到宿主机 将宿主机文件拷贝到容器内 docker cp 要拷贝的宿主机文件或目录 容器名称:容器文件或目录 1. 在宿主机上创建一个mengxuegu文件并写入内容 2. 将mengxuegu文件拷贝进 mycentos2 容器中的 /opt 目录下(mycentos2要是UP启动状态) 3. 登录 mycentos2 容器,查看/opt目录下是否有 mengxuegu 文件 从容器内文件拷贝到宿主机

隔离 docker 容器中的用户

笔者在前文<理解 docker 容器中的 uid 和 gid>介绍了 docker 容器中的用户与宿主机上用户的关系,得出的结论是:docker 默认没有隔离宿主机用户和容器中的用户.如果你已经了解了 Linux 的 user namespace 技术(参考<Linux Namespace : User>),那么自然会问:docker 为什么不利用 Linux user namespace 实现用户的隔离呢?事实上,docker 已经实现了相关的功能,只是默认没有启用而已.笔者将在

实例演示如何在spring4.2.2中集成hibernate5.0.2并创建sessionFactory

本文地址:http://blog.csdn.net/sushengmiyan/article/details/49388209 文章作者:苏生米沿 本文目的:使用spring4.2.2集成hibernate5.0.2并创建sessionFactory实例. 开发环境:eclipse(jee_mars) JDK1.8 MYSQL5.6 spring下载地址: https://repo.spring.io/list/release/org/springframework/spring/4.2.2.R

非阻塞算法在并发容器中的实现【转】

转自:https://www.ibm.com/developerworks/cn/java/j-lo-concurrent/ 非阻塞算法在 Java 中的应用越来越广泛 , ConcurrentLinkedQueue 是 java. concurrent 包中基于非阻塞算法实现的并发容器的典范.通过本文,您将了解非阻塞算法的工作原理及其在 ConcurrentLinkedQueue 中的具体实现机制. 简介 非阻塞算法在更细粒度的层面协调争用,它比传统的锁有更高的并发性.随着非阻塞算法在 Jav