当前位置: 首页 > news >正文

【unique_str 源码学习】

文章目录

    • 1.删除器定义
    • 2. operator->() 运算符重载
    • 3. add_lvalue_reference<element_type>::type 使用

基本原理这篇博主写的很详细

https://yngzmiao.blog.csdn.net/article/details/105725663

1.删除器定义

deleter_type& get_deleter() noexcept                  // 获取删除器
{ return std::get<1>(_M_t); }

在这里插入图片描述
在这里插入图片描述

2. operator->() 运算符重载

pointer operator->() const noexcept                   // 智能指针->运算符
{_GLIBCXX_DEBUG_ASSERT(get() != pointer());          // 断言 get() 不等于 pointer()return get();                                        // 返回 get() 的值
}

这个函数的作用是:

  1. 断言:在 operator->() 函数内部,首先调用 _GLIBCXX_DEBUG_ASSERT 函数来断言 get() != pointer()。这意味着 std::unique_ptr 的 get() 方法返回的指针不能等于 std::unique_ptr 自身的指针。这是为了确保 std::unique_ptr 的 get() 方法返回的指针是有效的,指向的是 std::unique_ptr 管理的对象。

  2. 返回指针:如果断言成功,operator->() 函数会返回 get() 方法返回的指针。get() 方法返回的是 std::unique_ptr 管理的对象的指针。

operator->() 函数的作用是允许用户通过 std::unique_ptr 对象访问其管理的对象的成员。例如,如果 std::unique_ptr 管理的是一个 MyClass 对象,你可以通过 ptr->member 的方式访问 MyClass 对象的成员,而不是通过ptr.get()->member 的方式。(内部实现是通过ptr.get()->member

请注意,operator->() 函数被声明为 noexcept,这意味着这个函数不会抛出异常。这对于智能指针的实现非常重要,因为智能指针需要在析构函数或 reset 方法中调用删除器,而不能抛出异常。

#include <iostream>
#include <memory>class MyClass {
public:int value;void print() const {std::cout << "Value: " << value << std::endl;}
};int main() {// 创建一个 MyClass 对象,并使用 std::unique_ptr 管理它std::unique_ptr<MyClass> ptr(new MyClass);ptr->value = 10;  // 使用 operator->() 访问 MyClass 对象的成员// 调用 MyClass 对象的成员函数ptr->print();return 0;
}

在这个示例中,我们首先定义了一个 MyClass 类,它有一个成员变量 int value 和一个成员函数 void print()。然后,我们使用 std::unique_ptr 来管理一个 MyClass 对象。

通过 ptr->value = 10; 和 ptr->print();,我们可以使用 std::unique_ptr 的 operator->() 运算符来访问和操作 MyClass 对象的成员。ptr->value = 10; 设置了 MyClass 对象的 value 成员为 10,而 ptr->print(); 调用了 MyClass 对象的 print 成员函数。

这个示例展示了如何使用 std::unique_ptr 和 operator->() 来管理和操作智能指针管理的对象。**

3. add_lvalue_reference<element_type>::type 使用

typename add_lvalue_reference<element_type>::type operator*() const   // 解引用
{_GLIBCXX_DEBUG_ASSERT(get() != pointer());return *get();
}

在上述代码中,typename add_lvalue_reference<element_type>::type operator*() const 定义了一个解引用操作符 *,用于解引用智能指针。add_lvalue_reference 是一个模板类,它用于将一个类型转换为左值引用类型。在这里,它用于将 element_type 转换为左值引用类型。

element_type 是一个模板参数,它表示智能指针所指向的元素类型。add_lvalue_reference<element_type>::type 返回 element_type 的左值引用类型。左值引用是一种引用类型,它允许你修改被引用的对象。

operator* 函数的作用是返回指针所指向的元素的左值引用。这意味着,当你使用 * 操作符解引用智能指针时,你将得到一个可以修改元素的左值引用。

例如,如果 element_type 是 int,那么 add_lvalue_reference<element_type>::type 将返回 int&,即 int 类型的左值引用。

_GLIBCXX_DEBUG_ASSERT(get() != pointer()); 这行代码是一个断言,用于确保智能指针的值不是空指针。在解引用操作时,如果智能指针的值是空指针,程序将抛出一个异常,因为你不能对空指针解引用。

return *get(); 这行代码返回指针所指向的元素的左值引用。get() 函数返回智能指针的值。*get() 将返回智能指针所指向的元素的左值引用。

例如,如果 element_type 是 int,那么 *get() 将返回一个 int& 类型的左值引用,你可以通过这个引用修改 int 类型的值。

请注意,operator* 函数的返回类型是 add_lvalue_reference<element_type>::type,这意味着它返回的是 element_type 的左值引用类型。在使用 operator* 解引用智能指针时,你将得到一个可以修改元素的左值引用。
在这里插入图片描述
在这个例子中,我们首先定义了一个模板类 add_lvalue_reference,它的作用是将一个类型转换为左值引用类型。然后,我们定义了一个智能指针类 SmartPtr,它使用 add_lvalue_reference 模板类来实现解引用操作。

在 main 函数中,我们创建了一个整数对象 num,然后创建了一个 SmartPtr 对象 sp,并将其指向 num。然后,我们使用解引用操作符 * 解引用 sp,得到一个可以修改 num 值的左值引用 ref。最后,我们修改了 num 的值,并输出其新的值。

这个例子展示了如何使用 SmartPtr 类的解引用操作符 * 来获取一个可以修改元素的左值引用。

http://www.lryc.cn/news/473875.html

相关文章:

  • flask第一个应用
  • 华为OD机试真题(Python/JS/C/C++)- 考点 - 细节
  • 【C++刷题】力扣-#628-三个数的最大乘积
  • Java项目实战II基于Java+Spring Boot+MySQL的工程教育认证的计算机课程管理平台(源码+数据库+文档)
  • 基于微信小程序实现信阳毛尖茶叶商城系统设计与实现
  • 设计一个灵活的RPC架构
  • 大数据计算里的Broadcast Hash Join/Shuffle Hash Join/Sort Merge Join
  • Java - 手写识别; 如何用spring ai和大模型做手写识别教程
  • 【Linux】用户权限管理:创建受限用户并配置特定目录访问权限
  • pgsql表分区和表分片设计
  • 灵动AI ——视频创作新引擎 开启视觉奇幻之旅
  • AI设计、作图、画画工具哪个好用?看完这篇你就知道怎么选了
  • 【python ASR】win11-从0到1使用funasr实现本地离线音频转文本
  • myqld二进制安装和破解数据库密码(linux)
  • 防重方案-订单防重方案笔记
  • HTML、JavaScript和CSS实现注册页面设计
  • Counter对象的使用样例
  • 大模型中的token是什么;常见大语言模型的 token 情况
  • Python小白学习教程从入门到入坑------第十七课 内置函数拆包(语法基础)
  • 动态规划 —— 路径问题-最小路径和
  • 《链表篇》---删除链表的倒数第N个节点(中等)
  • duilib 进阶 之 TileListBox 列表
  • Web应用安全—信息泄露
  • 大数据治理:策略、技术与挑战
  • vscode插件-08 Golang
  • 数据结构+算法分析与设计[15-18真题版]
  • 单链表OJ题(2):反转链表(三指针法)、找中间节点(快慢指针)
  • Rows 行
  • 十个常见的软件测试面试题,拿走不谢
  • windows 11 配置 kafka 使用SASL SCRAM-SHA-256 认证