auto_ptr:動態記憶體管理的安全衛士動態記憶體管理中,new/delete 配對看似簡單,但異常拋出會打斷正常控制流,導致 delete 無法執行:
void g() { if (cond) throw X(); }
void func() {
string* pstr = new string;
g(); // 若拋出異常
delete pstr; // 永不執行 → 記憶體洩漏
}
局部自動變數(棧上物件)在異常展開棧時會自動呼叫解構函數,天然安全。但鏈表、STL 容器、資料庫連線等**必須**使用動態分配。
std::auto_ptr:RAII 解決方案C++98 標準庫引入 <memory> 中的 std::auto_ptr,以**擁有權轉移**語義管理單一動態物件生命週期。
#include
#include
using namespace std;
void func() {
auto_ptr pstr(new string); // 建構時取得擁有權
*pstr = "hello"; // 重載 operator* / operator->
pstr->size();
// 離開作用域自動 delete pstr,異常安全
}
auto_ptr<T> p = new T;(編譯錯誤)。*、->:像原始指標一樣使用。delete:棧展開時保證釋放。auto_ptr<char> p(new char[10]) 會用 delete 而非 delete[] → 未定義行為。auto_ptr 複製/賦值會**轉移擁有權**,來源變為 null:
auto_ptr pw1(new Widget);
auto_ptr pw2(pw1); // pw1 變 null,pw2 擁有 Widget
pw1 = pw2; // pw2 變 null,pw1 重獲擁有權
這違反標準複製語義,導致**嚴重缺陷**:
vector<auto_ptr<T>> 排序/複製時會讓元素變 null、物件被過早刪除。auto_ptr 作為容器元素。shared_ptr (C++11) 或 boost::shared_ptr。vector、unique_ptr<T[]> (C++11) 或 scoped_array。auto_ptr 是 C++98 產物,C++11 引入 unique_ptr(移動語義、支援陣列、可放入容器)與 shared_ptr(共享擁有權)徹底取代它。C++17 標記 auto_ptr 為**棄用**,C++20 **移除**。
理解 auto_ptr 的 RAII 思想與擁有權轉移缺陷,是掌握現代 C++ 智慧指標體系的關鍵基石。新代碼請直接使用 unique_ptr/shared_ptr。