C++中如何實現(xiàn)自定義刪除器 智能指針中自定義資源釋放方法

c++++中使用智能指針時,若需自定義資源釋放邏輯,可通過綁定刪除器實現(xiàn),具體方式因指針類型而異。1. unique_ptr需顯式指定刪除器類型并傳入函數(shù)或仿函數(shù),如void my_deleter(myresource* ptr),構(gòu)造時傳遞其地址;2. shared_ptr可直接接受可調(diào)用對象作為刪除器,無需額外模板參數(shù),支持函數(shù)、Lambda、仿函數(shù)等;3. 設(shè)計刪除器時應(yīng)避免拋出異常、避免捕獲外部狀態(tài)的lambda、注意刪除器類型影響指針兼容性,并避免耗時操作。例如管理文件句柄時可用lambda執(zhí)行fclose。掌握這些要點有助于正確高效地處理特殊資源。

C++中如何實現(xiàn)自定義刪除器 智能指針中自定義資源釋放方法

c++ 中使用智能指針時,如果默認的資源釋放方式不滿足需求(比如操作的是非內(nèi)存資源、需要特殊清理邏輯等),就需要自定義刪除器。智能指針如 std::unique_ptr 和 std::shared_ptr 都支持傳入自定義刪除器來控制資源釋放過程。

C++中如何實現(xiàn)自定義刪除器 智能指針中自定義資源釋放方法


1. unique_ptr 如何綁定自定義刪除器

unique_ptr 默認會調(diào)用 delete 來釋放資源,但你可以通過模板參數(shù)指定刪除器類型,并在構(gòu)造時傳入具體的刪除函數(shù)或仿函數(shù)。

C++中如何實現(xiàn)自定義刪除器 智能指針中自定義資源釋放方法

基本寫法:

立即學(xué)習(xí)C++免費學(xué)習(xí)筆記(深入)”;

void my_deleter(MyResource* ptr) {     // 自定義清理邏輯     delete ptr; }  std::unique_ptr<MyResource, decltype(&my_deleter)> ptr(new MyResource(), &my_deleter);

注意這里必須顯式指定第二個模板參數(shù)為函數(shù)指針類型,否則編譯器無法推導(dǎo)出刪除器類型。

C++中如何實現(xiàn)自定義刪除器 智能指針中自定義資源釋放方法

如果你希望更簡潔地管理刪除器,可以用 lambda 表達式結(jié)合 std::function 或者使用 std::unique_ptr 的別名模板。


2. shared_ptr 更靈活的刪除器支持

相比 unique_ptr,shared_ptr 在構(gòu)造時可以直接接受一個可調(diào)用對象作為刪除器,不需要額外指定模板參數(shù),使用起來更加方便。

示例:

auto my_deleter = [](MyResource* ptr) {     // 執(zhí)行一些清理工作     delete ptr; };  std::shared_ptr<MyResource> ptr(new MyResource(), my_deleter);

這里的刪除器可以是函數(shù)、lambda、仿函數(shù),甚至 std::function 對象。shared_ptr 內(nèi)部會拷貝這個刪除器并保存下來,在最后一個引用失效時調(diào)用它。

需要注意的一點是,刪除器和資源是綁定在一起的,即使你把 shared_ptr 轉(zhuǎn)換成了指向基類的指針,刪除器也會保持正確的行為。


3. 刪除器的設(shè)計注意事項

設(shè)計刪除器時有幾個細節(jié)容易被忽略:

  • 刪除器不能拋出異常:因為資源釋放通常發(fā)生在析構(gòu)過程中,一旦拋出異常可能導(dǎo)致程序崩潰。
  • 避免捕獲外部狀態(tài)的 lambda:如果你用了帶捕獲的 lambda 做刪除器,確保其生命周期足夠長,或者不會造成懸空引用。
  • 刪除器類型會影響智能指針的類型:對于 unique_ptr,不同的刪除器會導(dǎo)致不同的指針類型,影響賦值兼容性。
  • 不要在刪除器中做耗時操作:尤其是在線程環(huán)境下,長時間執(zhí)行刪除器可能會影響性能。

舉個例子,如果你管理的是文件句柄或其他系統(tǒng)資源,刪除器里可能不只是 delete,還可能是 fclose、close(fd) 等:

auto file_deleter = [](FILE* f) { if (f) fclose(f); }; std::shared_ptr<FILE> fp(fopen("test.txt", "r"), file_deleter);

這樣就能安全地自動關(guān)閉文件了。


基本上就這些。自定義刪除器雖然不是每天都要用的功能,但在處理特殊資源時非常有用,理解它的使用方式和限制能讓你寫出更健壯的代碼。

? 版權(quán)聲明
THE END
喜歡就支持一下吧
點贊12 分享