C++ 如何使用std::shared_ptr作为类成员?

C++ 如何使用std::shared_ptr作为类成员?,c++,c++11,memory-management,smart-pointers,C++,C++11,Memory Management,Smart Pointers,我需要创建一个这样的类。但当我运行此代码时,我得到: "Error in `./a.out': free(): invalid next size (fast)" 我的班级怎么了?如何将shared_ptr正确用作类成员 #include <memory> class MyClass { public: MyClass(unsigned size) { _size = size; _arr = std::make_shared<int

我需要创建一个这样的类。但当我运行此代码时,我得到:

"Error in `./a.out': free(): invalid next size (fast)"
我的班级怎么了?如何将shared_ptr正确用作类成员

#include <memory>

class MyClass
{
public:
    MyClass(unsigned size) {
        _size = size;
        _arr = std::make_shared<int>(size);
        for (int i = 0; i < size; i++)
            _arr.get()[i] = 0;
    }

    MyClass(const MyClass& other) {
        _arr = other._arr;
        _size = other._size;
    }

    MyClass& operator=(const MyClass& other) {
        _arr = other._arr;
        _size = other._size;
    }

    void setArr(std::shared_ptr<int> arr, unsigned size) {
        _size = size;
        _arr = arr;
    }

    ~MyClass() {
        _arr.reset();
    }

private:
    std::shared_ptr<int> _arr;
    unsigned _size;
};

int main() {
    MyClass m(4);
    return 0;
}
#包括
类MyClass
{
公众:
MyClass(无符号大小){
_大小=大小;
_arr=标准::使_共享(大小);
对于(int i=0;i
谢谢你,我误解了分享的意义。如果我想使用int*(不是std::vector或std::array),我应该写这个吗?(不要修改其他方法)

MyClass(无符号大小){
_大小=大小;
_arr=std::shared_ptr(新int[size]);
对于(int i=0;i
请看看它是如何工作的

基本上,std::make_共享

构造类型为T的对象并将其包装在std::shared_ptr中

在您的例子中,T是int,因此std::make_shared创建了int类型的对象,并将其包装在std::shared_ptr中。因此,内存分配给单个int,而不是int数组,并且您的程序会导致未定义的行为

我想您可以使用以下方法来避免问题:

_arr = std::shared_ptr<int>(new int[size], std::default_delete<int[]>());
_arr=std::shared_ptr(新的int[size],std::default_delete());
还请注意:

  • 运算符=不返回任何内容
  • 变量名称不应以下划线开头
  • 不必在类析构函数中为_arr调用reset() 拜托,看看是怎么回事

    基本上,std::make_共享

    构造类型为T的对象并将其包装在std::shared_ptr中

    在您的例子中,T是int,因此std::make_shared创建了int类型的对象,并将其包装在std::shared_ptr中。因此,内存分配给单个int,而不是int数组,并且您的程序会导致未定义的行为

    我想您可以使用以下方法来避免问题:

    _arr = std::shared_ptr<int>(new int[size], std::default_delete<int[]>());
    
    _arr=std::shared_ptr(新的int[size],std::default_delete());
    
    还请注意:

  • 运算符=不返回任何内容
  • 变量名称不应以下划线开头
  • 不必在类析构函数中为_arr调用reset()
    提示:指针不是数组。仔细想想这意味着什么:
    std::使_共享(大小)。还请注意,您的问题与作为数据成员的智能指针无关。您说“需要创建这样的类”,并且不“想使用”简易标准解决方案(
    std::vector
    )。为什么?您绝对必须使用
    std::shared\u ptr
    的原因是什么?@anatolysultanov:您是否考虑过
    std::shared\u ptr
    ?@anatolysultanov:是的,您确实需要“动态数组”(即真正代码中的
    std::vector
    ,除非您有一个非常特殊的用例需要手动使用新的位置)如果大小仅在运行时已知。只有在程序运行前知道大小时,才能使用
    std::array
    。永远不要使用
    new[]
    。提示:指针不是数组。仔细想想这意味着什么:
    std::使_共享(大小)。还请注意,您的问题与作为数据成员的智能指针无关。您说“需要创建这样的类”,并且不“想使用”简易标准解决方案(
    std::vector
    )。为什么?您绝对必须使用
    std::shared\u ptr
    的原因是什么?@anatolysultanov:您是否考虑过
    std::shared\u ptr
    ?@anatolysultanov:是的,您确实需要“动态数组”(即真正代码中的
    std::vector
    ,除非您有一个非常特殊的用例需要手动使用新的位置)如果大小仅在运行时已知。只有在程序运行前知道大小时,才能使用
    std::array
    。只是永远不要使用
    new[]
    std::vector
    不会有相同的所有权语义。这实际上可能是一件好事,但不是OP的目标。您应该按值传递std::shared_ptr,因为它是指针抽象。还可以将std::shared_ptr与适当的deleter一起使用。@anatolysultanov
    setArr
    方法被破坏,因为您可以传递与“size”或shared_ptt的数组不匹配的大小。只需删除它,以及赋值运算符、复制构造函数和析构函数,然后使用编译器为您制作的模板。@AnatoliySultanov:如果事先知道数字10,那么您可以使用
    std::shared\u ptr
    并制作
    MyClass
    模板。请注意,您真正的问题已经与原始问题(如何使用
    std::shared_ptr
    作为类成员)有很大的不同
    std::vector
    将不具有相同的所有权语义。这实际上可能是一件好事,但不是OP的目标。您应该按值传递std::shared_ptr,因为它是指针抽象。还可以将std::shared_ptr与适当的deleter一起使用。@anatolysultanov
    setArr
    方法被破坏,因为您可以传递与“size”或shared_ptt的数组不匹配的大小。只需删除它,以及赋值运算符、复制构造函数和析构函数,然后使用编译器为您制作的模板。@AnatoliySultanov:如果事先知道数字10,那么您可以使用
    std::shared\u ptr
    并制作
    MyClass
    模板。请注意,您真正的问题已经与原来的问题(如何将
    std::shared_ptr
    用作类成员)有很大的不同