Before we begin dealing with how various versions of polymorphism are implemented in C++, let's first refresh the most basic. Let's start with a definition. What is polymorphism? Polymorphism is the ability of a function or an object with the same name to behave differently based on different types of input. So for example, let's look at this code here. Here, we have example of overloaded operators less than operator, greater than operator, redirect left, or rather, redirect out. As well as the template, get max. All of these are example of what's known as static-polymorphism. Why static? Because C++ is a compiled language and polymorphism could occur based on the runtime information where an object may behave differently based on the way it has been set up at runtime. Or objects may be created differently at compile time. Static polymorphism is also known as compiled time polymorphism, because the objects that we have here such as operator less than greater than, are created at compile time and do not change at runtime. Now let's look at dynamic or runtime polymorphism. Dynamic polymorphism has two main examples. One is function overriding, which is what we have here. Where we have a class person which has function first name and last name. And then you have class students, which also has a function first name and last name basically overriding the behavior of the same function in the person class. So if you set up a class student like I have here, the function will output student first name this and student last name this. Let us demonstrate. Compile and run. Now you see first name, student first name John student last name Smith. We know that this is actually coming from student. The other method that is more commonly used than the previous one is the method we'd refer to as derived object by its base class point or a reference and use a virtual function. So let's demonstrate. Let's change the definition to virtual. And let's create an output function using person reference as the class. And instead of calling output directly, let's call function output name. Now let's run it. And the output you see is exactly the same as before, although we're calling the object with a reference to a person. So what should we calling these functions, an output person first, person last, although we don't. How would that become possible is discussed in the next section.