C + + Learning notes--re-recognition of virtual function and polymorphism __ function

Source: Internet
Author: User
Tags modifier knowledge base

Since watching "Effective C + +", more and more feel that they should learn C + +. But pick up from the bits and pieces of knowledge and go slowly.


Polymorphism

When the same object receives a different message or a different object receives the same message, it produces a different implementation action. C + + supports two types of polymorphism: compile-time polymorphism, Run-time polymorphism.
A. Compile-time polymorphism: implemented by overloaded functions
B run-time polymorphism: implemented by virtual functions.

Classes that contain pure virtual functions are called abstract classes. Because an abstract class contains a pure virtual function that is not defined, you cannot define an object for an abstract class.

  

Refer to the following text:

  

What exactly did the compiler do to implement the late binding of virtual functions? Let's find out what's going on.

The compiler creates a table (called V TA B L E) for each class that contains a virtual function. In v TA B L E, the compiler places the virtual function address of a particular class. In each class with a virtual function, the compiler secretly put a pointer, called V P o i n T e R (abbreviated to V P t r), pointing to the V TA B L E of this object. When a virtual function call is made through a base class pointer (that is, a long state call), the compiler statically inserts the code that obtains the V P T R and looks for the address of the function in the V TA B L e table, so that the correct function can be invoked to make the late bundle happen. Set v TA B L E, initialize v P R, and insert code for virtual function calls for each class, so we don't have to worry about that. With a virtual function, the appropriate function of this object can be invoked even if the compiler does not know the specific type of the object. ("C + + programming Ideas")

The following is from the VC knowledge Base


Three, the structure of virtual function in memory

1. Let's take a look at an example:

#include "iostream.h"
#include "string.h"

Class A {
Public
virtual void Fun0 () {cout << "a::fun0" << Endl;}
};


int main (int argc, char* argv[])
{
A A;
cout << "Size of A =" << sizeof (a) << Endl;
return 0;
}

The result is as follows: Size of A = 4

2. If you add another virtual function: virtual void fun1 () {cout << "a::fun" << Endl;}
Get the same result. If you remove the virtual modifier in front of the function

Class A {
Public
void Fun0 () {cout << "a::fun0" << Endl;}
};


int main (int argc, char* argv[])
{
A A;
cout << "Size of A =" << sizeof (a) << Endl;
return 0;
}

The result is as follows: Size of A = 1

3. Looking at the following results:

Class A {
Public
virtual void Fun0 () {cout << "a::fun0" << Endl;}
int A;
int b;
};
int main (int argc, char* argv[])
{
A A;
cout << "Size of A =" << sizeof (a) << Endl;
return 0;
}

The result is as follows: Size of A = 12

In fact, virtual functions are structured in memory in this way:


Figure I

Under window2000 The pointer occupies 4 bytes in memory, and the virtual function saves the address of the function in a virtual function table (VTABLE). Look at the example below.

Class A {
Public
virtual void Fun0 () {cout << "a::fun0" << Endl;}
virtual void fun1 () {cout << "a::fun1" << Endl;}
int A;
int b;
};
int main (int argc, char* argv[])
{
A A;
cout << "Size of A =" << sizeof (a) << Endl;
return 0;
}

The results are as follows:
Size of A = 4

The memory structure of the virtual function is as follows, you can also through the function pointer, first find the virtual function table (VTABLE), and then access to each function address to verify the structure, in the foreign web site author is: Zeeshan Amjad wrote "ATL on the Hood" is described in detail.


Figure II

4. Let's take a look at the memory structure of the virtual function in the inheritance, first look at the following example

Class A {
Public
virtual void F () {}
};
Class B {
Public
virtual void F () {}
};
Class C {
Public
virtual void F () {}
};
Class Drive:public A, public B, public C {
};
int main () {
Drive D;
cout << "Size is =" << sizeof (d) << Endl;
return 0;
}

The results are as follows: the Size is = 12, I believe you will see the following structure diagram is very clear,


Figure Three

5. Let's take a look at a virtual function to achieve polymorphism, first look at an example:

Class A {
Public
virtual void F () {cout << "a::f" << Endl;}
};
Class B:p ublic a{
Public
virtual void F () {cout << "b::f" << Endl;}
};
Class C:p ublic A {
Public
virtual void F () {cout << "c::f" << Endl;}
};
Class Drive:public C {
Public
virtual void F () {cout << "d::f" << Endl;}
};

int main (int argc, char* argv[])
{
A A;
b b;
c C;
Drive D;
A.F ();
B.f ();
C.F ();
D.F ();
return 0;
}
Result: A::f
B::f
C::f
D::f

No need to explain, I believe everyone can see what the truth. Note: Polymorphism is not a function overload

6. Implementing a dynamic connection with virtual functions during compilation, the C + + compiler determines that the program uses that function, based on the arguments that the program passes to the function, or the function return type, and then the compiler replaces each startup with the correct function. This compiler-based substitution is called a static connection, and they are executed before the program is run. On the other hand, when a program executes polymorphism, the substitution occurs during the execution of the program, which is called a dynamic connection. The following example:

Class a{
Public
virtual void F () {cout << "a::f" << Endl;};
};

Class B:public a{
Public
virtual void F () {cout << "b::f" << Endl;};
};
Class C:public a{
Public
virtual void F () {cout << "c::f" << Endl;};
};
void Test (A *a) {
A->f ();
};
int main (int argc, char* argv[])
{
b *b=new B;
c *c=new C;
char choice;
do{
cout<< "Type B for class B,c for class C:" <<endl;
cin>>choice;
if (choice== ' B ')
Test (b);
else if (choice== ' C ')
Test (c);
}while (1);
cout<<endl<<endl;
return 0;
}

In the example above, if you remove the virtual modifier from the class a,b,c, look at the printed result, and then look at the following example to see the connection between the two. If you remove the virtual modifier in B and C, what happens, the result is the same as not being removed.

7. Call a function of an inherited class in the base class (if this function is a virtual function) or look at the example first:

Class A {
Public
virtual void fun () {
cout << "A::fun" << Endl;
}
void Show () {
Fun ();
}
};

Class B:public A {
Public
virtual void fun () {
cout << "B::fun" << Endl;
}
};

int main () {
A A;
A.show ();

return 0;
}

Print Results: A::fun

In the example in 6, test (a *a) actually has a process in which an inherited class pointer implicitly converts to a base-class pointer. We can see that using virtual functions we can invoke inherited class functions in the base class. However, if it is not a virtual function, the inheriting class pointer can only call the base class function after it has been converted to a base class pointer. Conversely, if the base class pointer transforms to an inherited class pointer, it can only be displayed and transformed, and the transformed inheriting class pointer may call the base class and the inheriting class pointer. The following example:

 class A {
public:
Void Fun () {
cout << "A::fun" << Endl;
}

};
Class B:public A {
Public:
Void Fun () {
cout << "B::fun" << Endl;
}
void Fun0 () {
cout << "B::fun0" << Endl;
}
};
Int main () {
a *a=new A;
b *b=new B;
A *pa;
B *PB;
Pb=static_cast<b *> (a);///base class pointers are displayed to inherited class pointers
Pb->fun0 ();
Pb->fun ()
return 0;
}

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.