c++智能指针(一)
作者:Rem ㅤ | 发布时间:
1. 智能指针的作用
避免申请的内存空间(栈)忘记主动释放而造成内存泄漏;在函数结束时自动释放内存空间。
2. 智能指针的分类
-
auto_ptr(c++98提出,c++11废弃):采⽤所有权模式。
auto_ptr<std::string> p1(new std::string("hello")); -
unique_ptr(替换auto_ptr):实现独占式拥有或严格拥有概念,保证同⼀时间内只有⼀个智能指针可以指向该对象。
unique_ptr<std::string> p1(new std::string("hello")); -
shared_ptr(共享型,强引用): 实现共享式拥有概念,多个智能指针可以指向相同对象,该对象和其相关资源会在“最后⼀个引⽤被销 毁”时候释放。
shared_ptr<std::string> p1(new std::string("hello")); -
weak_ptr(弱引用):⽤来解决 shared_ptr 相互引⽤时的死锁问题。
shared_ptr<std::string> p1(new std::string("hello")); weak_ptr<std::string> p2 = p1;
3. auto_ptr
在使用new动态申请对象后,不会自动调用对象的析构函数,如果不手动使用delete释放空间就会造成内存泄漏,此时也可以选择使用智能指针。
#include <iostream>
#include <memory>
using namespace std;
class Test_1
{
public:
Test_1() : data(0) { cout << "Test_1 constructor called" << endl; } // constructor for Test_1 class
~Test_1() { cout << "Test_1 destructor called" << endl; } // destructor for Test_1 class
private:
int data;
};
int main(int argc, char **argv)
{
Test_1 *test_1 = new Test_1();
system("pause");
return 0;
}
结果:

析构函数没有执行。
使用智能指针auto_ptr:
#include <iostream>
#include <memory>
using namespace std;
class Test_2
{
public:
Test_2() : data(0) { cout << "Test_2 constructor called" << endl; } // constructor for Test_2 class
~Test_2() { cout << "Test_2 destructor called" << endl; } // destructor for Test_2 class
int GetData() { return this->data; }
private:
int data;
};
int main(int argc, char **argv)
{
auto_ptr<Test_2> pTest_2(new Test_2);
cout << pTest_2->GetData() << endl;
cout << (*pTest_2).GetData() << endl;
system("pause");
return 0;
}
调用Test_2中的GetData方法,结果:

直接在控制台是看不到析构函数的调用的,因为析构函数在变量生存期结束之后执行,在次程序中在main函数结束才会执行。
修改为在其他函数中调用:
#include <iostream>
#include <memory>
using namespace std;
class Test_2
{
public:
Test_2() : data(0) { cout << "Test_2 constructor called" << endl; } // constructor for Test_2 class
~Test_2() { cout << "Test_2 destructor called" << endl; } // destructor for Test_2 class
int GetData() { return this->data; }
private:
int data;
};
void Fun()
{
auto_ptr<Test_2> pTest_2(new Test_2);
cout << pTest_2->GetData() << endl;
cout << (*pTest_2).GetData() << endl;
}
int main(int argc, char **argv)
{
Fun();
system("pause");
return 0;
}
结果:

可以看到析构函数被调用。用同样的方法测试没有使用智能指针的情况依然没有调用析构函数,读者可以自行尝试。
auto_ptr被弃用的主要原因:复制或者赋值都会改变资源的所有权
#include <iostream>
#include <memory>
using namespace std;
class Test_2
{
public:
Test_2() : data(0) { cout << "Test_2 constructor called" << endl; } // constructor for Test_2 class
~Test_2() { cout << "Test_2 destructor called" << endl; } // destructor for Test_2 class
int GetData() { return this->data; }
private:
int data;
};
int main(int argc, char **argv)
{
auto_ptr<Test_2> pTest2_1(new Test_2);
auto_ptr<Test_2> pTest2_2(new Test_2);
cout << "Test_2 object 1 address: " << pTest2_1.get() << endl; // prints "Test_2 object 1 address
cout << "Test_2 object 2 address: " << pTest2_2.get() << endl; // prints "Test_2 object 2 address
pTest2_1 = pTest2_2;
cout << "Test_2 object 1 address: " << pTest2_1.get() << endl; // prints "Test_2 object 1 address
cout << "Test_2 object 2 address: " << pTest2_2.get() << endl; // prints "Test_2 object 2 address
system("pause");
return 0;
}
结果:

在指针赋值之后pTest2_2变为NULL。
标签:c/c++