1. 程式人生 > >C++ this指針詳解

C++ this指針詳解

既然 動態 color 直接 除了 size 替換 全局 程序修改

this指針: 每個成員函數都有一個隱含的輸入參數this指針,this指向當前對象,this指針可以用來訪問對象的數據成員。
class B {
public:
       void fun1() {
       }
       void fun() const{
             printf("成員函數地址:%x\n", &B::fun1);
             printf("成員數據x的地址:%x\n", &x);
             printf("成員數據y的地址:%x\n", &y);
             printf(
"當前對象地址:%x\n", this); printf("當前對象的this指針類型:%s\n", typeid(this).name()); printf("\n"); } int x; int y; }; int main() { B b1, b2; const B b3; b1.fun(); b2.fun(); b3.fun(); }

結果:

成員函數地址:f8114f
成員數據x的地址:cffd94
成員數據y的地址:cffd98
當前對象地址:cffd94
當前對象的this指針類型:
class B const * 成員函數地址:f8114f 成員數據x的地址:cffd84 成員數據y的地址:cffd88 當前對象地址:cffd84 當前對象的this指針類型:class B const * 成員函數地址:f8114f 成員數據x的地址:cffd74 成員數據y的地址:cffd78 當前對象地址:cffd74 當前對象的this指針類型:class B const *

結論:成員函數是屬於類的,成員數據是屬於對象的。 程序修改成:
class B {
public:
       
void fun1() { } void fun() const{ printf("成員函數地址:%x\n", &B::fun1); printf("成員數據x的地址:%x\n", &x); printf("成員數據y的地址:%x\n", &y); printf("當前對象地址:%x\n", this); printf("當前對象的this指針類型:%s\n", typeid(this).name()); printf("\n"); } void fun() { printf("成員函數地址:%x\n", &B::fun1); printf("成員數據x的地址:%x\n", &x); printf("成員數據y的地址:%x\n", &y); printf("當前對象地址:%x\n", this); printf("當前對象的this指針類型:%s\n", typeid(this).name()); printf("\n"); } int x; int y; }; int main() { B b1, b2; const B b3; b1.fun(); b2.fun(); b3.fun(); }

結果:

成員函數地址:931ac8
成員數據x的地址:12ffbb4
成員數據y的地址:12ffbb8
當前對象地址:12ffbb4
當前對象的this指針類型:class B *
 
成員函數地址:931ac8
成員數據x的地址:12ffba4
成員數據y的地址:12ffba8
當前對象地址:12ffba4
當前對象的this指針類型:class B *
 
成員函數地址:931ac8
成員數據x的地址:12ffb94
成員數據y的地址:12ffb98
當前對象地址:12ffb94
當前對象的this指針類型:class B const *

結論:當前this指針的類型不僅與對象(const or not)有關,還與對象所調用的成員函數有關。 那麽,為什麽可以用this指針訪問成員函數呢?
class B {
public:
    void fun1() {
        printf("fun1()\n");
    }
    void fun2() {
        this->fun1();
    }
};

猜測:每個對象都需要訪問成員函數,那麽,該對象裏一定復制了類的成員函數(應該放在內存的程序段)的地址;既然對象與類有關,那麽對象裏除了數據成員之外,肯還有其他與類相關的信息。

還有一種可能是,類的成員函數在編譯時都修飾成類名有關的名稱,這個名稱變成了全局唯一的函數名,這些函數都應該放在內存的代碼段位置;當對象訪問成員函數時,將直接使用修飾過後的名稱來調用;而非類的對象調用類的成員函數時,無法使用修飾過的函數名,所以訪問出錯。這樣看來,通過this指針訪問成員函數,與直接訪問成員函數沒有區別,或者說this指針與成員函數沒有關系。之所以允許這種寫法,是為了讓人看上去更直觀一些。

static成員函數與this指針:

static成員函數沒有默認將this指針參數,所以static成員無法訪問對象的數據,只能訪問static數據成員。

為什麽說this指針不是對象的一部分?this指針所占用的內存不會反應在sizeof的結果中?

this指針是動態構造的,只有在調用非靜態成員函數時,才臨時構造並傳入到成員函數的形參中,調用完畢則被銷毀(與形參的屬性一致),猜測這就是平時並不占用對象的內存的原因。

虛函數中的this指針:

在虛函數所在類中,有一張虛函數表,而類的對象則有一個虛表指針,指向這張虛表。當虛函數被子類的函數覆蓋(重寫)時,虛函數表中的相應位置的函數指針將被替換成子類的函數指針。this指針相當於虛表指針?

C++ this指針詳解