传统的手动管理内存方式(如 new
和 delete
)虽然灵活,但也容易引发内存泄漏(new的对象在作用域结束后没有被及时释放)、悬空指针(指针的指向对象已被删除或释放,但仍有其他指针保留了对该内存位置的引用)和重复释放(一个指针指向的内存被多次重复释放)等问题。随着项目规模的扩大和代码复杂性的增加,这些问题不仅让程序员疲于奔命,也直接影响了软件的可靠性和可维护性。
智能指针就是为了实现类似于Java中的垃圾回收机制。Java的垃圾回收机制使程序员从繁杂的内存管理任务中彻底的解脱出来,在申请使用一块内存区域之后,无需去关注应该何时何地释放内存,Java将会自动帮助回收。但是出于效率和其他原因(可能C++设计者不屑于这种傻瓜氏的编程方式),C++本身并没有这样的功能,其繁杂且易出错的内存管理也一直为广大程序员所诟病。
更进一步地说,智能指针的出现是为了满足管理类中指针成员的需要。包含指针成员的类需要特别注意复制控制和赋值操作,原因是复制指针时只复制指针中的地址,而不会复制指针指向的对象(一块内存地址可能被多个对象所指向)。当类的实例在析构的时候,可能会导致垂悬指针问题(即指针的指向对象已被删除或释放,但仍有其他指针保留了对该内存位置的引用)。
**管理类中指针成员的方法一般有两种方式:**一种是采用值型类,这种类是给指针成员提供值语义(value semantics),当复制该值型对象时,会得到一个不同的新副本。这种方式典型的应用是string类。另外一种方式就是智能指针,实现这种方式的指针所指向的对象是共享的。
智能指针不仅提供了内存管理的自动化,还增强了代码的安全性和可读性,是现代 C++ 中推荐的内存管理方式之一。本篇文章旨在系统地介绍 C++ 标准库中的三种常用智能指针:std::unique_ptr
、std::shared_ptr
和 std::weak_ptr
。
智能指针并不是指针,而是行为类似于指针的类对象,这种对象具有指针不包含的其他功能。简单来说,智能指针能帮助我们管理动态分配的内存,它会帮助我们自动释放new出来的内存,从而避免 new
和 delete
引发的一系列问题,比如内存泄漏、悬空指针和重复释放等。
C++里面有四个智能指针:auto_ptr、share_ptr、unique_ptr、weak_ptr。其中后三个是C++11支持的,并且第一个已经在C++11弃用,这里我们只学习后三个。