Depth profiling function pointer

Source: Internet
Author: User

Disclaimer: The following code is all compiled in Windows7 vs2010 environment and is executed without error.

global function pointers

is a pointer to a function variable , at C compile time, each function has an entry address, then this function pointer to this functions point to this address.

function pointers are used in large, two main roles: as arguments for calling functions and functions.

How to declare a function pointer:

Data type identifier ( pointer variable name )(parameter list);

The Declaration of a general function is:

IntFunc (int x);

A function pointer is declared as follows:

Int (*func) (INTX);

The preceding (*FUNC) bracket is necessary, which tells the compiler that we are declaring a function pointer instead of declaring a function with a return type as a pointer, and the subsequent parameter depends on the function parameter that the function pointer points to.

However, this statement is sometimes very cumbersome, so typedef can come in handy, we can also declare:

Typedefint (*PF) (int x);

PF PF;

So PF is a function pointer, which facilitates a lot. Func (x) or (*FUCN) (x) is good when you want to use a function pointer to invoke a function, and of course, the function pointer can also point to the overloaded function, and the compiler will differentiate the overloaded functions for us so that the function pointer points to the correct function.

Method for calling function pointers:

(*PF) (x);

PF (x);


int Fun (inti) {cout<< "Call fun\n"; returni;} int _tmain (INTARGC, _tchar* argv[]) {typedefint (*pfun) (int);//function pointer type definition; pfun pf1 = fun;//pointer assignment & symbol is dispensable here; Pfun PF2 = &A MP;FUN;PF1 (5);//Function call * symbol dispensable (*PF2) (6);p funpfarr[] = {fun,&fun};//function pointer array; pfarr[0] (7);//function pointer array call; (*pfarr[1]) (8) ; Int (*parr[5]) (int);//definition of function pointer array parr[0] = Fun;fun (9); return 0;}
Global function pointer usage A simple comment has been made to say no more.


Pointers to member functions

is a pointer variable to a member function, and at C compile time, each member function has an entry address, and the function pointer to this function points to the address. Compared to a pointer to a function, the scope of the function is declared, defined, and called by an entity or pointer of a class of objects.

Okay, no more nonsense, cut into the subject.

How to declare a function pointer:

Data type identifier ( function scope:: pointer variable name )(parameter list);

A function pointer is declared as follows:

Int (CLASSNAME::* func) (int x);

Similar to global function pointers.

However, we sometimes find it very cumbersome to declare typedef can come in handy, we can also declare:

Typedefint (CLASSNAME::* PF) (int x);

PF PF;

is similar to a global pointer.

You can also declare a pointer to a class member variable:

Int (CLASSNAME::* pi) = classname::m_i; This is not the focus of the detailed introduction.

Method for calling function pointers:

(OBJECT.*PF) (x);

(OBJECTPOINT->*PF) (x);

Example: Case 1

How to declare, invoke a pointer to a member function


Classfuncptr{public:void Show (inti) {cout<< "Call Funcptr::show" <<i<<endl;}}; int _tmain (INTARGC, _tchar* argv[]) {typedefvoid (funcptr::* pfun) (int); Funcptrfptr;funcptr *pfptr = Newfuncptr ();p Fun PF1 = &funcptr::show;//must use & Fetch function address;//pfun PF2 = funcptr::show;//compile error; use "&funcptr::show" to create a pointer to a member;//(*PF1 ) (5); Compilation error (FPTR.*PF1) (6);(p Fptr->*pf1) (7);d eletepfptr;}

Case 2

If a function pointer is defined inside a class, how do you call it as a member variable? Take a look at my example below.

Classfuncptr{public:typedefvoid (funcptr::* pfun) (int);p funpf;public:funcptr () {pf = &funcptr::show;} void Show (Inti) {cout<< "Call Funcptr::show" <<I<<ENDL; Voidcallfuncptr (inti) {return (THIS->*PF) (i);}}; int _tmain (INTARGC, _tchar* argv[]) {funcptrfuncp;//* (FUNCP.PF) (8);//compilation error, equivalent to (*PF1) (5);;( funcp.* (FUNCP.PF)) (9);//borrowing class entities to achieve; Funcp.callfuncptr (10);}

(funcp.* (FUNCP.PF)) (9); // can be realized by borrowing class entities;

It is so troublesome to call function pointers directly with the member variables of an object, so it is recommended that you define a function in the class that invokes the function pointer.


Voidcallfuncptr (inti) {(THIS->*PF) (i);}

Case 3

What if you define a class-a member function pointer in class B?

Class funcptr{public:typedefvoid (funcptr::* pfun) (int);p Fun pf;public:funcptr () {pf = &funcptr::show;} void Show (Inti) {cout<< "Call Funcptr::show" <<I<<ENDL; void Show2 (Inti) {cout<< "Call Funcptr::show2" <<I<<ENDL;} Voidcallfuncptr (inti) {return (THIS->*PF) (i);}}; Class Other{private:funcptr M_funcp;public:typedefvoid (funcptr::* pfun) (int);p Funpf;public:other () {}other (inti) { if (1 = = i) {pf = &funcptr::show;} ELSE{PF = &funcptr::show2;}} void Callfunptr (INTI,FUNCPTR&FUNCP)//In this case, it is important to have an external incoming object intern or a pointer to it. {return (funcp.* (THIS->PF)) (i);}}; int _tmain (INTARGC, _tchar* argv[]) {funcptr funcp;//* (FUNCP.PF) (8);//compilation error, equivalent to (*PF1) (5);;( funcp.* (FUNCP.PF)) (9);//borrowing class entities to achieve; funcp.callfuncptr; other oth1 (1);//define two different object entities let the same function pointer point to the unused function; other oth2 (2) ; Oth1.callfunptr (11,der);//Incoming required funcptr entity class; Oth2.callfunptr (12,der);}

Case 4

What happens if a class inherits and derives? The inheritance in C + + itself is a very complex thing, and the different compilers do different internal processing for us, which always makes the programmer feel confused. Knowing undeterred, let's try it. What happens when a simple single inheritance is inherited?

Case 4.1

Simple inheritance does not extend and overwrite


classderive:publicfuncptr{//Nothing in the sub-class, all directly with the parent class;}; int _tmain (INTARGC, _tchar* argv[]) {funcptrfuncp;derive der;//This is simply replacing the parent class object with a derived class object, which is obviously satisfying the "is-a" relationship;//* (FUNCP.PF) (8) ;//Compile error, equivalent to (*PF1) (5);;( Der.* (DER.PF)) (9);//Borrowing class entities to be implemented; der.callfuncptr; other oth1 (1);//define two different object entities so that the same function pointer points to different functions; other oth2 (2); O Th1.callfunptr (11,der);//Incoming required funcptr entity class; Oth2.callfunptr (12,der);}

Derive der; // in this case, it is simply replacing the parent object with a derived class object, which obviously satisfies the "is-a" relationship;

There is no difference between a derived class and a base class.

Case 4.2

Derived classes override and override functions in a base class

Classfuncptr{public:typedefvoid (funcptr::* pfun) (int);p Fun pf;public:funcptr () {pf = &funcptr::show;} void Show (Inti) {cout<< "Call Funcptr::show" <<I<<ENDL; virtual void Show2 (inti)//The virtual function is written here; {cout<< "Call Funcptr::show2" <<I<<ENDL;} Voidcallfuncptr (inti) {return (THIS->*PF) (i);}}; Class derive:publicfuncptr{public:derive () {}void Show (inti) {cout<< "Call Derive::show" <<I<<ENDL;} Virtualvoid Show2 (inti) {cout<< "Call Derive::show2" <<i<<endl;}}; int _tmain (INTARGC, _tchar* argv[]) {derive der;//This is simply replacing the parent class object with a derived class object, apparently satisfying the "is-a" relationship; Der.callfuncptr (10);}

When a derived class calls its inherited function pointer, it ignores the show that the derived class overrides the subclass; The function pointer points to the function address of the base class and calls the show () function of the base class;

However, if the

PF = &funcptr::show; rewritten as

PF = &funcptr::show2;//Note that Show2 is a virtual function.





The function pointer then points to the function address of the derived class and invokes the overridden function of the derived class. after the base class has been derived, if the derived class overrides the virtual function of the base class, the corresponding virtual function address in the list of virtual functions of the base class is also modified to the derived virtual function address, in order to realize the polymorphism of C + + . The Deep exploration of the C + + object model gives a very detailed explanation, which is not explained here.


case 4.3

function pointers are defined in other non-derived classes

Class Other{private:funcptrm_funcp;public:typedefvoid (funcptr::* pfun) (int), where the scope of the Pfun has been set to Funcptr::;p FUNPF; Public:other () {}other (inti) {if (1 = = i) {PF = &funcptr::show;//has determined the scope of the function when assigning a value to the function pointer;} ELSE{PF = &funcptr::show2;}} Voidcallfunptr (INTI,FUNCPTR&FUNCP)//In this case it is important to have an external object intern or a pointer available. {return (funcp.* (THIS->PF)) (i);//There is no relationship to the borrowed object entity;}}; int _tmain (INTARGC, _tchar* argv[]) {funcptrfuncp;derive der;//This is simply replacing the parent class object with a derived class object, which is obviously satisfying the "is-a" relationship;//* (FUNCP.PF) (8) ;//Compile error, equivalent to (*PF1) (5);; /(Der.* (DER.PF)) (9);//borrowing class entities to achieve;//der.callfuncptr; other oth1 (1);//define two different object entities so that the same function pointer points to different functions; other oth2 (2); O Th1.callfunptr (11,FUNCP);//Funcptr entity class to be imported, oth1.callfunptr (12,der); oth1.callfunptr (13,FUNCP); Oth1.callfunptr ( 14,der);}

If the function pointer is defined externally, the scope of the function is determined at the beginning of the definition and has no relation to the borrowed object entity;

Class Other{private:funcptrm_funcp;public:typedefvoid (derive::* pfun) (int), where the scope of the Pfun has been set to Funcptr::;p FUNPF; Public:other () {}other (inti) {if (1 = = i) {PF = &derive::show;//has determined the scope of the function when assigning a value to the function pointer;} ELSE{PF = &derive::show2;}} Voidcallfunptr (inti,derive* FUNCP)//It is important to have an external object intern or a pointer available here. {return (funcp->* (THIS->PF)) (i);//There is no relationship to the borrowed object entity;}}; int _tmain (INTARGC, _tchar* argv[]) {funcptrfuncp;derive der;//This is simply replacing the parent class object with a derived class object, which is obviously satisfying the "is-a" relationship;//* (FUNCP.PF) (8) ;//Compile error, equivalent to (*PF1) (5);; /(Der.* (DER.PF)) (9);//borrowing class entities to achieve;//der.callfuncptr; other oth1 (1);//define two different object entities so that the same function pointer points to different functions; other oth2 (2); O Th1.callfunptr (11,dynamic_cast<derive*> (&FUNCP));//Funcptr entity class to be imported; Oth1.callfunptr (12,&der); o Th1.callfunptr (13,dynamic_cast<derive*> (&FUNCP)); Oth1.callfunptr (14,&der);}


Summarize:

The above analysis has been very deep, if the reader can read here, then believe that the function pointer has been fully understood.

To the full extent of the complaint:

In General, a word , function pointer is the function entry address , The following are summarized according to different kinds of pointers separately .

the global function pointer holds the entry address of the function, which is beyond doubt.

function pointers for member functions

1. a non-virtual function is the entry address of the function;

2. The virtual function is the address value of the corresponding virtual function in the list of virtual functions of the object, and it is possible that the derived class has rewritten the virtual function. It can also be understood to record the low amount of virtual functions in the virtual function list, rather than the address values of the virtual functions.

Please correct me if there is any indication of the wrong place.






Depth profiling function pointer

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.