scoped_ptr是Boost庫中的一個智能指針,它和auto_ptr非常類似,可以完成資源的自動釋放。scoped_ptr與auto_ptr的區別在於,auto_ptr可以實現資源的轉移,但是scoped_ptr禁止了資源的轉移,它讓一個對象擁有了對資源的徹底掌控。
下面代碼模擬實現了scoped_ptr:
template <class T>
class ScopedPtr
{
public:
ScopedPtr(T* ptr)
:_ptr(ptr)
{}
T& operator *()//返回所指向的對象
{
return *this;
}
T* operator ->()//使用->調用智能指針對象的函數
{
return _ptr;
}
T* get()//獲取裸指針
{
return _ptr;
}
~AutoPtr()
{
Destroy();
}
protected:
void Destroy()
{
if (_ptr)
{
delete _ptr;
_ptr = NULL;
}
}
private:
ScopedPtr(ScopedPtr<T>& ob);
ScopedPtr<T>& operator =(ScopedPtr<T>& ob);
T* _ptr;
};
注意:要禁止資源的轉移,所以將它的拷貝構造函數和複製運算符的重載都給成私有的,這樣就防止了資源的轉移
缺點:
- 不能轉換權限
scoped_ptr所管理的對象生命週期僅僅侷限於一個區間(該指針所在的"{}"之間),無法傳到區間之外,這就意味着scoped_ptr對象是不能作爲函數的返回值的(auto_ptr可以)。 -
不能共享所有權
這個特點使得該指針簡單易用,但是造成了指針功能的薄弱,讓它不能用於stl的容器中。
-
不能用於管理數組對象
由於scoped_ptr是通過delete來刪除所管理對象,所以不能管理數組對象。
Boost庫中給出了scoped_array進行對new[] 申請出來的空間進行管理。它的實現原理和scoped_ptr是一樣的。
下面的代碼是模擬實現scoped_array:
template <class T>
class ScopedArray
{
public:
ScopedArray()
{}
ScopedArray(T* ptr)
:_ptr(ptr)
{}
T* get()//獲取裸指針
{
return _ptr;
}
T& operator [](int num)const
{
return _ptr[num];
}
~ScopedArray()
{
Destroy();
}
protected:
void Destroy()
{
if (_ptr)
{
delete[] _ptr;
_ptr = NULL;
}
}
private:
ScopedArray(ScopedArray<T>& ob);
ScopedArray<T>& operator =(ScopedArray<T>& ob);
T* _ptr;
};
scoped_array和scoped_ptr的不同:
-
scoped_array構造函數接受的必須是new[]的結果,scoped_ptr構造函數接受的必須是new的結果
-
scoped_array必須使用delete[]釋放資源,scoped_ptr必須使用delete釋放資源
-
scoped_array沒有 *和->這兩個操作符的重載,它是一個指向一段空間的指針
-
scoped_array提供了[]的重載,可以像普通數組一樣使用下標訪問
注意:雖然Boost庫中有scoped_array這個只能指針,不過最好在需要動態分配數組時使用vector來完成
vector可以實現任意類型的動態數組,而且他有豐富的成員函數來操作數據,易於維護。而對於scoped_array來說,它僅僅是對指針的管理,不能動態增長也沒有迭代器支持,相對來說難於使用。