詳解C++中的成員訪問運(yùn)算符和指針到成員運(yùn)算符
成員訪問運(yùn)算符:. 和 ->
語法
postfix-expression
. name
postfix-expression –> name
備注
成員訪問運(yùn)算符 . 和 -> 用來引用結(jié)構(gòu)、聯(lián)合和類的成員。成員訪問表達(dá)式具有選定成員的值和類型。
有兩種形式的成員訪問表達(dá)式:
在第一種形式中,postfix-expression 表示結(jié)構(gòu)、類或聯(lián)合類型的值,name 為指定的結(jié)構(gòu)、聯(lián)合或類的成員命名。運(yùn)算的值是 name 的值且為左值(如果 postfix-expression 是左值)。
在第二種形式中,postfix-expression 表示指向結(jié)構(gòu)、聯(lián)合或類的指針,name 為指定的結(jié)構(gòu)、聯(lián)合或類的成員命名。該值是 name 的值且是左值。 –> 運(yùn)算符取消引用該指針。因此,表達(dá)式 e–>member 和 (*e).member(其中,e 表示指針)會(huì)產(chǎn)生相同的結(jié)果(重載運(yùn)算符 –> 或 * 的情況除外)。
以下示例演示成員訪問運(yùn)算符的兩種形式。
// expre_Selection_Operator.cpp // compile with: /EHsc #include <iostream> using namespace std; struct Date { Date(int i, int j, int k) : day(i), month(j), year(k){} int month; int day; int year; }; int main() { Date mydate(1,1,1900); mydate.month = 2; cout << mydate.month << "/" << mydate.day << "/" << mydate.year << endl; Date *mydate2 = new Date(1,1,2000); mydate2->month = 2; cout << mydate2->month << "/" << mydate2->day << "/" << mydate2->year << endl; delete mydate2; }
這樣的話出來的兩個(gè)值分別為:
2/1/1900 2/1/2000
指針到成員運(yùn)算符:.* 和 ->*
語法
expression .* expression
expression –>* expression
備注
指向成員的指針運(yùn)算符(.* 和 –>*)返回表達(dá)式左側(cè)上指定的對象的特定類成員的值。右側(cè)必須指定該類的成員。下面的示例演示如何使用這些運(yùn)算符:
// expre_Expressions_with_Pointer_Member_Operators.cpp // compile with: /EHsc #include <iostream> using namespace std; class Testpm { public: void m_func1() { cout << "m_func1\n"; } int m_num; }; // Define derived types pmfn and pmd. // These types are pointers to members m_func1() and // m_num, respectively. void (Testpm::*pmfn)() = &Testpm::m_func1; int Testpm::*pmd = &Testpm::m_num; int main() { Testpm ATestpm; Testpm *pTestpm = new Testpm; // Access the member function (ATestpm.*pmfn)(); (pTestpm->*pmfn)(); // Parentheses required since * binds // less tightly than the function call. // Access the member data ATestpm.*pmd = 1; pTestpm->*pmd = 2; cout << ATestpm.*pmd << endl << pTestpm->*pmd << endl; delete pTestpm; } Output m_func1 m_func1
結(jié)果分別為:
1 2
在前面的示例中,指向成員的指針 pmfn 用于調(diào)用成員函數(shù) m_func1。另一個(gè)指向成員的指針 pmd 用于訪問 m_num 成員。
二元運(yùn)算符 .* 將其第一操作數(shù)(必須是類類型的對象)與其第二操作數(shù)(必須是指向成員的指針類型)組合在一起。
二元運(yùn)算符 –>* 將其第一操作數(shù)(必須是指向類類型的對象的指針)與其第二操作數(shù)(必須是指向成員的指針類型)組合在一起。
在包含 .* 運(yùn)算符的表達(dá)式中,第一操作數(shù)必須是類類型且可訪問,而指向第二操作數(shù)中指定的成員的指針或可訪問類型的成員的指針明確從該類派生并且可供該類訪問。
在包含 –>* 運(yùn)算符的表達(dá)方式中,第一操作數(shù)必須是第二操作數(shù)中指定的類型的“指向類類型的指針”或明確地從該類派生的類型。
考慮以下類和程序段:
// expre_Expressions_with_Pointer_Member_Operators2.cpp // C2440 expected class BaseClass { public: BaseClass(); // Base class constructor. void Func1(); }; // Declare a pointer to member function Func1. void (BaseClass::*pmfnFunc1)() = &BaseClass::Func1; class Derived : public BaseClass { public: Derived(); // Derived class constructor. void Func2(); }; // Declare a pointer to member function Func2. void (Derived::*pmfnFunc2)() = &Derived::Func2; int main() { BaseClass ABase; Derived ADerived; (ABase.*pmfnFunc1)(); // OK: defined for BaseClass. (ABase.*pmfnFunc2)(); // Error: cannot use base class to // access pointers to members of // derived classes. (ADerived.*pmfnFunc1)(); // OK: Derived is unambiguously // derived from BaseClass. (ADerived.*pmfnFunc2)(); // OK: defined for Derived. }
指向成員的指針運(yùn)算符 .* 或 –>* 的結(jié)果是在指向成員的指針的聲明中指定的類型的對象或函數(shù)。因此,在前面的示例中,表達(dá)式 ADerived.*pmfnFunc1() 的結(jié)果是指向返回 void 的函數(shù)的指針。如果第二操作數(shù)是左值,則此結(jié)果為左值。
System_CAPS_note注意
如果某個(gè)指向成員的指針運(yùn)算符的結(jié)果是函數(shù),則該結(jié)果只能用作函數(shù)調(diào)用運(yùn)算符的操作數(shù)。
相關(guān)文章
C語言運(yùn)算符的優(yōu)先級和結(jié)合性實(shí)例詳解
本文主要介紹C語言運(yùn)算符的知識,這里對運(yùn)算符的優(yōu)先級和結(jié)合性做出了詳解,并附實(shí)例代碼,希望能幫助有需要的小伙伴2016-07-07淺析c#中如何在form的webbrowser控件中獲得鼠標(biāo)坐標(biāo)
以下是對c#中如何在form的webbrowser控件中獲得鼠標(biāo)坐標(biāo)的實(shí)現(xiàn)方法進(jìn)行了詳細(xì)的分析介紹,需要的朋友可以參考下2013-07-07C/C++中一次性執(zhí)行多個(gè)DOS命令的實(shí)現(xiàn)思路
在C語言中執(zhí)行DOS命令的方法很多,在這就不一給大家一一介紹了,本文重點(diǎn)給大家介紹C/C++中一次性執(zhí)行多個(gè)DOS命令的實(shí)現(xiàn)思路,需要的朋友參考下2017-12-12學(xué)習(xí)C和C++的9點(diǎn)經(jīng)驗(yàn)總結(jié)
本文給大家總結(jié)了一下我們在學(xué)習(xí)C和C++的時(shí)候的一些經(jīng)驗(yàn)和需要注意的事項(xiàng),希望能給大家一些幫助,少走些彎路2015-12-12OpenCV使用BSM統(tǒng)計(jì)視頻中移動(dòng)的對象
這篇文章主要為大家詳細(xì)介紹了OpenCV如何使用BackgroundSubstractor(BSM)實(shí)現(xiàn)視頻中移動(dòng)對象統(tǒng)計(jì)功能,文中的示例代碼講解詳細(xì),需要的可以參考一下2023-02-02