【问题标题】:Delete the smartpointer object?删除智能指针对象?
【发布时间】:2012-09-10 10:54:14
【问题描述】:

背景:
在阅读智能指针时,我遇到了以下 C++ 中智能指针的示例实现

template < typename T > class SP
{
    private:
    T*    pData; // Generic pointer to be stored
    public:
    SP(T* pValue) : pData(pValue)
    {
    }
    ~SP()
    {
        delete pData;
    }

    T& operator* ()
    {
        return *pData;
    }

    T* operator-> ()
    {
        return pData;
    }
};

class Person
{
    int age;
    char* pName;

    public:
        Person(): pName(0),age(0)
        {
        }
        Person(char* pName, int age): pName(pName), age(age)
        {
        }
        ~Person()
        {
        }

        void Display()
        {
            printf("Name = %s Age = %d \n", pName, age);
        }
        void Shout()
        {
            printf("Ooooooooooooooooo",);
        } 
};

void main()
{
    SP<Person> p(new Person("Scott", 25));
    p->Display();
    // Dont need to delete Person pointer..
}

问题:

  1. 此智能指针的好处是一旦超出范围就会删除 Person 类对象。但是那我们是否需要专门添加代码“delete p;”?在 main 函数中,以便智能指针类不会泄漏自己?

  2. 既然Person类也有析构函数,我们真的需要对person的对象调用delete吗?当 Person 对象超出范围时,将自动调用析构函数

【问题讨论】:

  • 不要使用这个实现。我不知道你在哪里找到它,但我觉得它是一个糟糕的来源,你应该避免使用它来学习严肃的 C++。这种实现违反了三法则,因此有害。
  • 您不再需要创建自己的智能指针,标准库有很好的实现供您使用。

标签: c++ smart-pointers


【解决方案1】:

[1] 在堆栈上分配p 时,您不需要删除它。如果你这样做了:

SP<Person>* p = new SP<Person>(new Person("Scott", 25));

那么你将不得不删除它。

[2] 您不需要在 Person 对象上调用 delete。这是由智能指针完成的——毕竟这是它的目的。

因此,您的代码在当前状态下没有任何内存泄漏。 然而,智能指针实现缺少复制构造函数、赋值运算符等,因此应添加它们以避免将来出现一些不希望的行为。

【讨论】:

  • @Lyubomir :感谢 Q[2] 的回答我的意思是问由于 person 类定义了析构函数,所以即使我们不为 Person 使用智能指针,person 类对象也会当它超出范围时在其析构函数调用中被销毁?
  • 它不依赖于它是否有析构函数。相反,它取决于如何声明变量。假设不使用智能指针,如果pPerson* p = new Person();,那么当您完成p 时,您必须手动调用delete。如果 pPerson p(); 则变量在堆栈上,当它超出范围时将自动销毁。
  • 也就是说总结一下:析构函数只对栈上的变量调用,
【解决方案2】:

不要使用那个实现。使用以下类(按优先顺序):

std::shared_ptr / std::unique_ptr (C++11).
std::tr1::shared_ptr / std::tr1::unique_ptr(Vis Studio 2008 支持 C++11 之前的版本)。
boost::shared_ptr / @987654326 @(如果您的编译器中不存在上述智能指针类)。

【讨论】:

  • 虽然您的言论是明智的,但他们并没有回答 OP 的问题。但是 +1,以抵消 -1。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-12-20
  • 2023-03-04
  • 1970-01-01
  • 2016-05-28
  • 2013-08-19
  • 1970-01-01
相关资源
最近更新 更多