C++智能指针的使用

C++智能指针的使用

1. 智能指针的作用

C++中普通的原始指针有两个主要问题:

  • 没有指针的所有权概念,导致资源管理困难
  • 没有指针生命周期跟踪,可能导致内存泄漏和野指针错误

智能指针正是为了解决上述问题而设计,它在原始指针的基础上增加了所有权及生命周期管理的功能。智能指针通常实现以下功能:

  • 过载indirection运算符(*)和member access运算符(->),提供和原始指针一样的用法
  • 负责指针指向对象的创建和释放
  • 防止内存泄漏
  • 当指针失效时防止野指针错误

总而言之,智能指针让原始C++指针变得更安全、简单,是一个非常有价值的现代C++技术。

2. 智能指针的类型

C++11中常用的智能指针有三种:

  • std::unique_ptr:独占式拥有权的智能指针,同一时间只能有一个unique_ptr指向一个对象。
  • std::shared_ptr:共享式拥有权的智能指针,多个shared_ptr可以指向同一个对象。
  • std::weak_ptr:弱引用式智能指针,指向一个由shared_ptr管理的对象。

下面逐一对其用法进行介绍。

3. std::unique_ptr的用法

std::unique_ptr实现独占式拥有权的语义,每个std::unique_ptr实例都完全控制所指向对象的生命周期,不允许其他智能指针共享所有权。主要用法有:

  • 创建std::unique_ptr:std::unique_ptr<T> ptr(new T());
  • 通过get()访问原始指针:T* rawPtr = ptr.get();
  • 转移所有权:std::unique_ptr<T> ptr2 = std::move(ptr1);
  • 释放指针:ptr.reset();

需要注意std::unique_ptr不支持复制,只能移动。
独占一个动态对象,禁止复制:

std::unique_ptr<Foo> p1(new Foo); 

// 编译错误,unique_ptr不能复制
std::unique_ptr<Foo> p2 = p1;  

// 正确,移动p1的所有权
std::unique_ptr<Foo> p3 = std::move(p1);

传递所有权:

void process(std::unique_ptr<Foo> ptr) {
  // 操作 ptr
}

std::unique_ptr<Foo> p(new Foo);
process(std::move(p)); 

4. std::shared_ptr的用法

std::shared_ptr实现共享式拥有权,多个std::shared_ptr实例可以共享同一个对象。用法包括:

  • 创建:std::shared_ptr<T> ptr(new T());
  • 复制:std::shared_ptr<T> ptr2 = ptr1;
  • 获取引用计数:std::size_t count = ptr.use_count();
  • 获取原始指针:T* rawPtr = ptr.get();

使用std::shared_ptr可以避免手动调用delete释放资源。
共享对象所有权:

std::shared_ptr<Foo> p1(new Foo);
std::shared_ptr<Foo> p2 = p1; // 共享 p1

防止循环引用导致内存泄漏:

struct Node {
  std::shared_ptr<Node> next;
  ~Node() { cout << "Destruct Node\n"; }
};

void processList(std::shared_ptr<Node> head) {
  std::shared_ptr<Node> curr = head;
  while(curr) {
    curr = curr->next; 
  }
} // head引用计数自动置零,节点可以释放

5. std::weak_ptr的用法

std::weak_ptr不控制对象生命周期,仅提供对std::shared_ptr管理对象的一个弱引用。主要用法有:

  • 从std::shared_ptr创建:std::weak_ptr<T> weakPtr(sharedPtr);
  • 使用expired()检查是否失效:if(weakPtr.expired()) {...}
  • lock()返回共享所有权:std::shared_ptr<T> sharedPtr = weakPtr.lock();

std::weak_ptr可以用来解决std::shared_ptr循环引用问题。
解决shared_ptr循环引用问题:

struct Node {
  std::weak_ptr<Node> next;
};

std::shared_ptr<Node> head(new Node());
head->next = head; // 不会循环引用
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值