C/C++中變量的可見性與生命期區別的本質原因

可見性與生命期

可見性又可稱爲:作用域,它是“棧”這種存儲方式的表現形式。不管是全局的可見性(全局作用域)、還是局部可見性(局部作用域),從一個對象(或稱爲變量、實例)的入棧(開始可見)到其出棧(變成不可見),是該對象的整個的作用域。

可見性與生命期是兩個分立的概念,但似乎又存在這某種聯繫。比如:如果一個對象變得不可見了,那麼似乎該對象的生命期也就結束了。而“堆”、“全局靜態區”、“常量區”這三種不同於“棧”的存儲方式卻又告訴我們,當對象不可見的時候,其生命期可能並沒有結束。。。。那麼到底是什麼造成了這兩種概念上的差異?而使得我們大多數初學C/C++語言的人的迷惑不解的呢?

答案就是:指針!!!

原因如下:

當我在上面的論述中提到“對象”(或稱變量、實例)的時候,其實,我並沒有將“對象本身”“對象所處的內存的地址”(即指針的值)加以區分。對於基本數據類型,往往很少用到這種區分,因爲基本類型的變量往往都直接存放在“棧”上(當然也可以通過動態內存分配將其放在堆中,如:int* p = new int(1);),所以不需要“間接尋址”(根據指針找到實際對應的對象)

而如果我們都是採用動態內存分配的方式,即用指針來表示其所對應的對象時(如:Object* o = new Object(); ),這種可見性和生命期 的分立就體現出來了:即指針對應的是可見性,而指針所指向的對象(也即指針所指向的內存)對應的是生命期。因爲指針是在棧上分配存儲的(指針也是一個變量),所以其可見性如前面所述,是棧這種存儲方式的表現形式。當指針出棧時,它本身不可見了,從而也間接的導致了它所指向的對象變得不可見,但這時這個對象本身的生命期並沒有結束,因爲對象本身並不是在棧上分配空間的。

這個時候,如果在其他函數或代碼中不再有任何指針保存該對象的地址,那麼這個對象就將不可以繼續被訪問,即該對象已經不可見了,但是其生命期併爲結束,所以對於的內存並未被收回。例 : 函數內的靜態變量,堆分配的變量 都可以屬於這種情況

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