命名空间
变体
操作

std::shared_ptr<T>::reset

来自 cppreference.com
< cpp‎ | memory‎ | shared ptr
 
 
实用工具库
语言支持
类型支持 (基本类型,RTTI)
库功能测试宏 (C++20)
动态内存管理
程序实用工具
协程支持 (C++20)
可变参数函数
调试支持
(C++26)
三方比较
(C++20)
(C++20)(C++20)(C++20)
(C++20)(C++20)(C++20)
通用实用工具
日期和时间
函数对象
格式化库 (C++20)
(C++11)
关系运算符 (C++20 中已弃用)
整数比较函数
(C++20)(C++20)(C++20)   
(C++20)
交换类型操作
(C++14)
(C++11)
(C++11)
(C++11)
(C++17)
通用词汇类型
(C++11)
(C++17)
(C++17)
(C++17)
(C++11)
(C++17)
(C++23)
基本字符串转换
(C++17)
(C++17)

 
动态内存管理
未初始化内存算法
约束未初始化内存算法
分配器
垃圾回收支持
(C++11)(直到 C++23)
(C++11)(直到 C++23)
(C++11)(直到 C++23)
(C++11)(直到 C++23)
(C++11)(直到 C++23)
(C++11)(直到 C++23)



 
 
void reset() noexcept;
(1) (自 C++11 起)
template< class Y >
void reset( Y* ptr );
(2) (自 C++11 起)
template< class Y, class Deleter >
void reset( Y* ptr, Deleter d );
(3) (自 C++11 起)
template< class Y, class Deleter, class Alloc >
void reset( Y* ptr, Deleter d, Alloc alloc );
(4) (自 C++11 起)

用由 ptr 指向的对象替换管理的对象。可选删除器 d 可供使用,稍后在没有shared_ptr 对象拥有它时用于销毁新对象。默认情况下,delete 表达式用作删除器。始终选择与提供的类型相对应的正确的 delete 表达式,这就是为什么该函数使用单独的参数 Y 作为模板实现的原因。

如果 *this 已经拥有一个对象并且它是拥有它的最后一个 shared_ptr,则该对象将通过拥有的删除器销毁。

如果由 ptr 指向的对象已被拥有,则该函数通常会导致未定义的行为。

1) 释放对管理对象的拥有权(如果有)。调用后,*this 不再管理任何对象。等效于 shared_ptr().swap(*this);.
2-4) 用由 ptr 指向的对象替换管理的对象。Y 必须是完整类型,并且可以隐式转换为 T。此外
2) 使用 delete 表达式作为删除器。必须有一个有效的 delete 表达式,即 delete ptr 必须是有效的、具有明确定义的行为并且不抛出任何异常。等效于 shared_ptr<T>(ptr).swap(*this);.
3) 使用指定的删除器 d 作为删除器。Deleter 必须可调用类型 T,即 d(ptr) 必须是良构的,具有明确定义的行为且不抛出任何异常。Deleter 必须是 可复制构造的,并且它的复制构造函数和析构函数不能抛出异常。等同于 shared_ptr<T>(ptr, d).swap(*this);.
4)(3) 相同,但此外还使用 alloc 的副本分配内部使用的數據。Alloc 必须是 分配器。复制构造函数和析构函数不能抛出异常。等同于 shared_ptr<T>(ptr, d, alloc).swap(*this);.

内容

[编辑] 参数

ptr - 指向要获取其所有权的对象的指针
d - 用于存储以删除对象的删除器
alloc - 用于内部分配的分配器

[编辑] 返回值

(无)

[编辑] 异常

2) std::bad_alloc 如果无法获取所需的额外内存。对于其他错误,可能会抛出实现定义的异常。 delete ptr 如果发生异常,则调用。
3,4) std::bad_alloc 如果无法获取所需的额外内存。对于其他错误,可能会抛出实现定义的异常。 d(ptr) 如果发生异常,则调用。

[编辑] 示例

#include <iostream>
#include <memory>
 
struct Foo
{
    Foo(int n = 0) noexcept : bar(n)
    {
        std::cout << "Foo::Foo(), bar = " << bar << " @ " << this << '\n';
    }
    ~Foo()
    {
        std::cout << "Foo::~Foo(), bar = " << bar << " @ " << this << '\n';
    }
    int getBar() const noexcept { return bar; }
private:
    int bar;
};
 
int main()
{
    std::cout << "1) unique ownership\n";
    {
        std::shared_ptr<Foo> sptr = std::make_shared<Foo>(100);
 
        std::cout << "Foo::bar = " << sptr->getBar() << ", use_count() = "
                  << sptr.use_count() << '\n';
 
        // Reset the shared_ptr without handing it a fresh instance of Foo.
        // The old instance will be destroyed after this call.
        std::cout << "call sptr.reset()...\n";
        sptr.reset(); // calls Foo's destructor here
        std::cout << "After reset(): use_count() = " << sptr.use_count()
                  << ", sptr = " << sptr << '\n';
    }   // No call to Foo's destructor, it was done earlier in reset().
 
    std::cout << "\n2) unique ownership\n";
    {
        std::shared_ptr<Foo> sptr = std::make_shared<Foo>(200);
 
        std::cout << "Foo::bar = " << sptr->getBar() << ", use_count() = "
                  << sptr.use_count() << '\n';
 
        // Reset the shared_ptr, hand it a fresh instance of Foo.
        // The old instance will be destroyed after this call.
        std::cout << "call sptr.reset()...\n";
        sptr.reset(new Foo{222});
        std::cout << "After reset(): use_count() = " << sptr.use_count()
                  << ", sptr = " << sptr << "\nLeaving the scope...\n";
    }   // Calls Foo's destructor.
 
    std::cout << "\n3) multiple ownership\n";
    {
        std::shared_ptr<Foo> sptr1 = std::make_shared<Foo>(300);
        std::shared_ptr<Foo> sptr2 = sptr1;
        std::shared_ptr<Foo> sptr3 = sptr2;
 
        std::cout << "Foo::bar = " << sptr1->getBar() << ", use_count() = "
                  << sptr1.use_count() << '\n';
 
        // Reset the shared_ptr sptr1, hand it a fresh instance of Foo.
        // The old instance will stay shared between sptr2 and sptr3.
        std::cout << "call sptr1.reset()...\n";
        sptr1.reset(new Foo{333});
 
        std::cout << "After reset():\n"
                  << "sptr1.use_count() = " << sptr1.use_count()
                  << ", sptr1 @ " << sptr1 << '\n'
                  << "sptr2.use_count() = " << sptr2.use_count()
                  << ", sptr2 @ " << sptr2 << '\n'
                  << "sptr3.use_count() = " << sptr3.use_count()
                  << ", sptr3 @ " << sptr3 << '\n'
                  << "Leaving the scope...\n";
    }   // Calls two destructors of: 1) Foo owned by sptr1,
        // 2) Foo shared between sptr2/sptr3.
}

可能的输出

1) unique ownership
Foo::Foo(), bar = 100 @ 0x23c5040
Foo::bar = 100, use_count() = 1
call sptr.reset()...
Foo::~Foo(), bar = 100 @ 0x23c5040
After reset(): use_count() = 0, sptr = 0
 
2) unique ownership
Foo::Foo(), bar = 200 @ 0x23c5040
Foo::bar = 200, use_count() = 1
call sptr.reset()...
Foo::Foo(), bar = 222 @ 0x23c5050
Foo::~Foo(), bar = 200 @ 0x23c5040
After reset(): use_count() = 1, sptr = 0x23c5050
Leaving the scope...
Foo::~Foo(), bar = 222 @ 0x23c5050
 
3) multiple ownership
Foo::Foo(), bar = 300 @ 0x23c5080
Foo::bar = 300, use_count() = 3
call sptr1.reset()...
Foo::Foo(), bar = 333 @ 0x23c5050
After reset():
sptr1.use_count() = 1, sptr1 @ 0x23c5050
sptr2.use_count() = 2, sptr2 @ 0x23c5080
sptr3.use_count() = 2, sptr3 @ 0x23c5080
Leaving the scope...
Foo::~Foo(), bar = 300 @ 0x23c5080
Foo::~Foo(), bar = 333 @ 0x23c5050

[编辑] 参见

构造新的 shared_ptr
(公有成员函数) [编辑]