智能指针
一.智能指针
•常规指针的缺点
–当一个常规指针离开它的作用域时,只有该指针变量本身所占据的内存空间(通常是4个字节)会被释放,而它所指向的动态内存并未得到释放
–在某些特殊情况下,包含free/delete/delete[]的代码根本就执行不到,形成内存泄漏
•智能指针的优点
–智能指针是一个封装了常规指针的类类型对象,当它离开作用域时,其析构函数负责释放该常规指针所指向的动态内存
–以正确方式创建的智能指针,其析构函数总会执行
智能指针与常规指针的一致性
–为了使智能指针也能象常规指针一样,通过“*”操作符解引用,通过“->”操作符访问其目标的成员,就需要对这两个操作符进行重载
•智能指针与常规指针的不一致性
–任何时候,针对同一个对象,只允许有一个智能指针持有其地址,否则该对象将在多个智能指针中被析构多次(double free)
–智能指针的拷贝构造和拷贝赋值需要做特殊处理,对其所持有的对象地址,以指针间的转移代替复制
–智能指针的转移语义与常规指针的复制语义不一致
二.auto_ptr
•标准库的auto_ptr,实现了智能指针的基本功能
–#include
–auto_ptr<目标类型> 智能指针对象 ( new操作符返回的目标对象地址);
–auto_ptr p (new Integer (100));
•auto_ptr的局限性
–不能跨作用域使用
–不能放入标准容器
–不能指向对象数组
操作符重载的限制
•不是所有的操作符都能重载,以下操作符不能重载
–作用域限定操作符(::)
–直接成员访问操作符(.)
–直接成员指针解引用操作符(.*)
–条件操作符(?:)
–字节长度操作符(sizeof)
–类型信息操作符(typeid)
•无法重载所有操作数均为基本类型的操作符
–int operator+ (int lhs, int rhs)
{
return lhs - rhs;
}
–x = 1 + 1; // x = 0 ?
•无法通过操作符重载改变操作符的优先级
–// z = x^y
Integer const operator^ (Integet const& x, int y)
{
Integer z (1);
for (int i = 0; i < y; ++i)
z.m_n *= x.m_n;
return z;
}
–d = a + b ^ c; // d = a + b^c ?
•无法通过操作符重载改变操作数的个数
–double operator% (Integer const& opd)
{
return opd.m_n / 100.0;
}
–x = 50%; // x = 0.5 ?
•无法通过操作符重载发明新的操作符
–// c2 = a2 + b2
Double const operator@ (Double const& a, Double const& b)
{
return Double (sqrt (a.m_d * a.m_d + b.m_d * b.m_d));
}
–c = 3.0 @ 4.0; // c = 5.0 ?
•操作符重载源自对一致性的追求,任何违反既有规则,甚至有悖于人类常识的实现,都应该尽可能地避免
–Complex const operator- (Complex const& lhs, Complex const& rhs)
{
return Complex (rhs.m_r - lhs.m_r, rhs.m_i - lhs.m_i);
}
–x = (3 + 4i) - (1 + 2i); // x = -2 - 2i ?
•操作符重载的价值在于提高代码的可读性,而不是成为某些别有用心的算符控们赖以卖弄的奇技淫巧