關於函式指標的作用域

2021-06-09 05:26:27 字數 1273 閱讀 2948

今天在mfc工程中使用了wm_user定義使用者訊息,從文件中得知on_message的訊息處理函式應該符合如下格式:afx_msg lresult (cwnd::*)(wparam, lparam)。其中的作用域"cwnd::"引起了我的好奇。我們知道,訊息處理函式只能在cwnd的派生類中定義或者過載,其作用域必然是cwnd派生類。為此我做了個實驗:

class parent

;class  child: public parent

};int main()

不能通過編譯。以基類為作用域的函式指標不可以接管派生類的成員函式。將**修改為:

class parent

};class  child: public parent

;int main()

順利通過編譯。以派生類為作用域的函式指標可以接管基類的成員函式。推測其原因如下:類的成員函式會接受該類的this指標作為隱藏引數。child類物件可以提供child類的this指標給parent::func(),使用派生類的指標為基類的指標賦值是安全的,因此編譯器允許這種行為。但是使用基類的指標為派生類的指標賦值是不安全的,因此編譯器不允許以基類為作用域的函式指標接管派生類的成員函式。

但是在mfc中我們卻看到了以cwnd::為作用域的函式指標接管在cwnd派生類的成員函式,這跟我們的實驗結果剛好相反。讓我們來看on_message的定義:

#define on_message(message, memberfxn) \

,。原來,cwnd派生類的成員函式在傳遞進on_message()之後進行了型別轉換,其作用域變成了cwnd::,自然可以被作用域為cwnd::的函式指標接管。如果沒有這一步操作,訊息處理函式根本進入不了對映表。

最後,讓我們通過例子來說明如何呼叫這個函式指標:

#include

using namespace std;

class parent

;class  child: public parent

void func()

這個例子首先讓乙個作用域為parent::的函式指標pointer接管了child::func,然後讓乙個parent指標呼叫pointer。執行結果是:螢幕上正確輸出m_val的值26。pointer知道child::m_val的存在!大家想想,如果pparent指標不是指向乙個child類物件,而是指向本類物件,會發生什麼樣的後果?就會發生越界訪問。因此,編譯器禁止以基類為作用域的函式指標接管派生類的成員函式。

mfc開發小組的大牛們利用巧妙的方式繞過了這個規則。但是嚴謹的規則可以幫助你不會輕易出錯。

函式 作用域 指標

實參與形參 值傳遞 實參賦值給形參之後,形參在函式體內發生的變化,不會傳回給實參 個數的對應關係 型別轉換 int result power 10 nslog d result int a 10 plus a nslog in main a d a fa 1,2,3,4,5 當無形參時,實參會被忽略...

函式過載與作用域,陣列指標

別名宣告的作用 例 typedef int arrt 10 using arrt int 10 arrt func int i arrt是含有10個整數的陣列的別名,因為無法返回陣列,所以將返回型別定義成陣列的指標,因此,func函式接受乙個int實參,返回乙個指向包含10個整數的陣列的指標。函式過...

函式的作用域

一,每乙個變數都是有作用域的。1,首先講一下 塊與作用域 for,if等語句還有 function,他們都有乙個特點,就是後面有一對 比如 for var i 0 i items.length i 之間有 if some express 之間有 function param1 之間有 所有 包起來的...