auto_ptr 使用详解 (C++98)
-
auto_ptr 是c++ 98定义的智能指针模板,其定义了管理指针的对象,可以将new 获得(直接或间接)的地址赋给这种对象。当对象过期时,其析构函数将使用delete 来释放内存!
-
用法:
头文件: #include < memory>
用 法: auto_ptr<类型> 变量名(new 类型)
-
例 如:
auto_ptr< string> str(new string("我要成为大牛~ 变得很牛逼!")); //string类型
auto_ptr<vector< int>> av(new vector<int>(10)); //int类型
Demo
#include <iostream>
#include <string>
#include <exception>
#include <memory>
using namespace std;
class Test {
public:
Test() { cout << "Test is construct" << endl; val = 666; }
~Test() { cout << "Test is destruct" << endl; }
int getVal() { return val; }
private:
int val;
};
void memory_leak_demo1() {
auto_ptr<Test>t (new Test());
//在使用智能指针访问对象的时候, 使用方式和普通指针一样
cout << t->getVal() << endl;
cout << (*t).getVal() << endl;
//release取消智能指针对动态内存的托管
//Test* tmp = t.release();
//delete tmp; //必须手动释放内存
//reset重置智能指针托管的内存地址,
//如果传递参数的地址不一致,原来的会被析构掉
t.reset(new Test());
}
int main(){
memory_leak_demo1();
system("pause");
return 0;
}
使用建议:
1.尽可能不要将auto_ptr 变量定义为全局变量或指针
2.除非自己知道后果,不要把auto_ptr 智能指针赋值给同类型的另外一个 智能指针
3.C++11 后auto_ptr 已经被“抛弃”,已使用unique_ptr替代!
auto_ptr陷阱
//弊端1. auto_ptr 被C++11 抛弃的主要理由 p1= p2 ,复制或赋值都会改变资源的所有权
auto_ptr<string> p1(new string("张三"));
auto_ptr<string> p2(new string("李四"));
printf("p1: %p\n", p1.get());
printf("p2: %p\n", p2.get());
p1 = p2;
printf("after p1 = p2\n");
printf("p1: %p\n", p1.get());
printf("p2: %p\n", p2.get());
//弊端2. 在 STL 容器中使用auto_ptr存在重大风险,
//因为容器内的元素必需支持可复制(copy constructable)和可赋值(assignable)。
vector<auto_ptr<string>> s1;
auto_ptr<string> p1(new string("张三"));
auto_ptr<string> p2(new string("李四"));
s1.push_back(move(p1));
s1.push_back(move(p2));
cout << s1[0].get() << endl;
cout << s1[1].get() << endl;
//赋值操作
s1[1] = s1[0];
cout << s1[0].get() << endl;
cout << s1[1].get() << endl;
//弊端3. 不支持对象数组的内存管理
auto_ptr<int[]> a1(new int[5]);
//auto_ptr陷阱4, 不能把多个auto_ptr类型的指针指向同一段内存地址
{
auto_ptr<string>t2;
string* str = new string("智能指针的内存管理陷阱");
t2.reset(str);
{
auto_ptr<string> t1;
t1.reset(str); //t1释放了 str 的内存
}
cout << *str << endl; //再次访问, 就会导致越界
} //作用域结束的时候, t2再次释放 str 内存