使用STL容器存儲複雜類對象時要注意的問題

問題情境:

最近想要通過實現一個非常簡單的線程池來練習編程思維(把想法轉換成流程圖?,然後將流程圖轉換成代碼)。現實再一次提醒了自己是有多麼菜。看似一個簡單的東西,花了好久去實現,過程中發現自己對於好多小的知識點一點都不熟練,比如 STL容器!!!

在我的代碼中有: 

class Job{

Job(_param_){

...

param = (LPVOID)malloc(size);

}

~Job(){

free(param);

LPVOID param;

LPFUNC func;

};

使用list<Job*> jobList; 來保存任務。

還有一個函數 GetJob(Job** pJob){...}


第一個問題:

在這個函數中,當有待執行的任務時,將通過指針從jobList中彈出一個任務,當使用pop_front/remove/erase時,都會導致容器中的對象被刪除,所以這是通過這個指針返回的對象在實際執行中會發生訪問無效內存空間的錯誤!!!


第二個問題:

在執行~Job(){...} 時,會發生內存訪問錯誤!!!

導致這個問題的原因: 在STL容器刪除對象的時候已經free過了?

有一個疑問,不是刪除Job對象的時候應該會調用Job的析構函數嗎?爲什麼在實際調用的時候會產生錯誤呢?

這是STL中碰到的問題!

很簡單,但是在實際使用中是很容被忽略的問題!


第三個問題:

由於返回的是指針,所以在將對象從jobList中刪除之前需要將Job的對象複製一份!

又由於Job對象中有從堆中分配的空間,所以如果使用默認的拷貝構造函數,系統只會默認的複製 param的地址,而不會重新分配一個空間給新對象的param然後再將param空間中的內容拷貝過來,因此在該Job對象被從容器中刪除的時候,由默認拷貝構造函數產生的對象中的param所指向的內容將變成無效內存空間!

解決辦法:

這個時候我們需要定義自己的拷貝構造函數,然後在函數中爲新的對象中的param指針分配一個新的空間,然後將舊的對象中的內容複製過來!如代碼:

class Job{

Job(Job& job){

paramsize = job.paramsize;

func = job. func;

param = (LPVOID)malloc(paramsize);

RtlCopyMemory(param,job.param,paramsize);

}

LPVOID param;

LPFUNC func;

int paramsize;

}


很多時候我們學習了很多東西,但我們知其然卻不知其所以然!

很早之前就學習過了拷貝構造函數,深拷貝,淺拷貝,但是可能忘記了,可能沒有深入的理解深拷貝,淺拷貝產生的原因和使用的場景!

知其然,也要知其所以然!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章