unique_ptr和shared_ptr有何区别?

在C++中,unique_ptrshared_ptr是两种重要的智能指针,主要区别如下:


1. 所有权机制

  • unique_ptr(独占指针)

    采用独占所有权 模式,同一时刻只能有一个unique_ptr指向资源,不可复制(copy禁止),仅支持移动语义move)。
    示例

    cpp 复制代码
    std::unique_ptr<int> ptr1 = std::make_unique<int>(10);
    std::unique_ptr<int> ptr2 = std::move(ptr1); // ptr1所有权转移至ptr2
  • shared_ptr(共享指针)

    采用共享所有权 模式,多个shared_ptr可指向同一资源,通过引用计数 管理资源生命周期。
    示例

    cpp 复制代码
    std::shared_ptr<int> ptr1 = std::make_shared<int>(20);
    std::shared_ptr<int> ptr2 = ptr1; // 引用计数+1

2. 实现原理

  • unique_ptr

    无额外开销,仅封装原始指针,通过删除器 (默认为delete)释放资源。
    内存占用 :接近原始指针大小(通常为sizeof(void*))。

  • shared_ptr

    维护控制块 (含引用计数、弱计数、删除器等),资源释放需计数归零。
    内存占用:通常为两个指针大小(指向资源和控制块)。


3. 使用场景

  • unique_ptr适用场景

    • 资源独占管理(如工厂模式返回值)
    • 替代auto_ptr(已废弃)
    • 性能敏感场景(无计数开销)
  • shared_ptr适用场景

    • 跨作用域共享资源(如多线程数据传递)
    • 复杂所有权关系(如网状数据结构)
    • 需自动管理生命周期时

4. 性能对比

特性 unique_ptr shared_ptr
复制开销 禁止复制 原子操作更新计数
内存占用 低(1指针) 较高(2指针+控制块)
线程安全 非原子操作 引用计数原子操作

5. 代码示例对比

cpp 复制代码
// unique_ptr:所有权转移
std::unique_ptr<int> u1 = std::make_unique<int>(5);
std::unique_ptr<int> u2 = std::move(u1); // u1变为nullptr

// shared_ptr:共享所有权
std::shared_ptr<int> s1 = std::make_shared<int>(10);
{
    std::shared_ptr<int> s2 = s1; // 计数=2
} // s2析构,计数=1
点击并拖拽以移动

总结

  • 独占资源 时用unique_ptr(高效、轻量)
  • 共享资源 时用shared_ptr(灵活、安全)
  • 避免循环引用(shared_ptr可能需配合weak_ptr
相关推荐
腾渊信息科技公司13 分钟前
Spring Boot对接MES实战:视觉检测数据自动同步方案
java·人工智能·spring boot·后端·计算机视觉·ai·软件需求
爱笑的源码基地1 小时前
高并发 Redis 缓存门诊HIS系统源码,含财务统计药房进销存
java·程序·门诊系统·诊所系统·云诊所源码
段一凡-华北理工大学1 小时前
向量数据库实战:选型、调优与落地~系列文章12:文本分块策略实战:chunk_size 怎么选?重叠多少?
开发语言·数据库·后端·oracle·rust·工业智能体·高炉智能化
Ljwuhe2 小时前
C++——多态
开发语言·c++
心平气和量大福大2 小时前
C#-WPF-Window主窗体
开发语言·c#·wpf
白露与泡影3 小时前
Arthas 实战指南:从方法耗时定位到 JVM 变量热修改
服务器·jvm·c#
莫逸风4 小时前
【AgentScope 2.0】 0. 学习指南
java·llm·agent·agentscope
从零开始的代码生活_4 小时前
C++ 继承详解:访问控制、对象模型、菱形继承与设计取舍
开发语言·c++·后端·学习·算法
云小逸4 小时前
【C++ 第七阶段:模板、泛型编程与工程综合详解】
开发语言·c++
z123456789864 小时前
2026最新两款AI编程工具深度对比实测
java·数据库·ai编程