Polymorphism – A Practical Example

Posted by Filip Ekberg on November 13 2008 2 Comments

Classes, inheritance and polymorphism can sometimes be somewhat hard to understand. So a practial example suits many well. Therefore this will be a tutorial where i will touch the areas of classes, pointers, inheritance and polymorphism.

So to just clearify some expressions i will add a little dictionary at the top:

Class
A class can somewhat be seen as a blueprint of your object. I.e. having a blueprint for a building, then this would be the class. Then a Constructor would build this to become an actuall touchable object.

Inheritance
When you inherit something you can think of it more like you extend this thing. I.e. having a Car and then having a Sports Car where there are some new variables to it. The Sports Car is actually a Car but it’s also extended with new properties.

Polymorphism
This is taken from Wikipedia: “In simple terms, polymorphism is the ability of one type, A, to appear as and be used like another type, B. In strongly typed languages, this usually means that type A somehow derives from type B, or type A implements an interface that represents type B”. Read more here

Pointer
For a pointer explenation look here

I will be using Visual Studio 2008 with the built in C++ compiler for the following examples.

A good practice will be to create a Bank, when you get a new assignment or just want to create something new, start by thinking about the structure, what actuall needs does this have? Well when creating a Bank i think to myself that i’d like to be able to create Bank Accounts, attatch these to People and you can go on and on.

But, for the example i will only go as far as creating a Bank, a Bank Account ( Abstract ) and a Student Bank account which is the only Bank account you can actually get.

So creating a simple diagram over the project, i got something like this:diagram So now we have a Bank, Account and Student Account, what kind of variables do we need?

Bank
Bank Name
Accounts

Account
Balance
Interest
Max Loan
Account Holder

Student Account
Amount of Deposits
Last Deposite Month

So the big difference between Account and Student Account is that the Student Account have different rules than Account and therefore calculate a lot of things differently. We won’t go through all the logics. There will of course be a window for you to evolve this application as you feel nessesary.

Now when we have a defined structure we can start by creating a new Project and it’s files. My project will be called Bank and the following files will be placed in it:

  1. main.cpp
  2. Bank.h
  3. Bank.cpp
  4. BankAccount.h
  5. BankAccount.cpp
  6. StudentAccount.h
  7. StudentAccount.cpp

When all my files are created a start by definint my program entry point, this being my main. Notice that i will be posting code snippets as pictures, because you should Write this yourself and not copy my code!

1

We prepare for an input/output stream by including <iostream> and setting using namespace std;

Now the next part is to define the Bank.h We need an appropriet constructor, desctructor and some access methods, remember to never open up member variables publicly!

The #ifndef part is important for the compiler, we dont want to define our header file more than once, because that is not nessesary!

2

I assume all the parts are clear except the last one, read more about how that pointer type works in the previous post here on my wordpress.

The implementation itself will be up to you, i will only be showing the structure, header-files and some code from main and where polymorphism is concerned!

The next file to create would be the BankAccount, remember to add #include “BankAccount.h”  to Bank.h when it has been done. Otherwise the BankAccount *accounts array will fail because undefined symbol.

Back to the third file, the BankAccount.h this is how i would structure it:

3

The part to look deeply on here is the Deposite method, watch closely, it’s defined as followed: virtual void Deposite(double amount) = 0; So this method is expected to be overrided in a inherited class and it has the return type of void and an in parameter of the type double.

Now the next file to create is the StudentAccount.h where we will be deriving from BankAccount.

4

So the following class StudentAccount is extending a class called BankAccount. So this means that StudentAccount is a BankAccount with extended properties and/or overrided functions.

Now, look closely again, here we have the virtual void Deposite part again, but without the =0, so this means we will be creating a definition for this function.

Also the Amount of Deposits and Last Deposit Month is just there to simulate some properties that might be nessesary to do something on a student accont. In my case this is for the Deposite. A Student Can’t deposite money more than three times per month, this is because a student gets 2% interest everytime they deposite money.

This is my Constructor for StudentAccount

5

As you can see, we pass the Variables Owner and Deposite back to the constructor of the base type, being BankAccount.

Now this is how my Deposite Method is implemented:

6 

Now the last think i want you to look at, is my final Main:

7

dth="450" border="0" />

I want you to try and create all the nessesary functions in Bank.cpp, BankAccount.cpp and in StudentAccount.ccp to get the following output from this Main.cpp:

8

I would happily answer any questions about this project. A link to the complete source code is here

Vote on HN

Pointers & Double Pointers

Posted by Filip Ekberg on November 11 2008 3 Comments

Definitions
First off, we need to clearify what a some of the expressions i will use mean. These are the following expressions:

Stack
Assuming that you know about a computer having RAM ( Random Access Memory ) which allows you to store information and have this accessable faster than you would on a secondary memory like a harddrive and/or cd-rom.

When a program is executed there is a part in the memory reserved for this application to use, this “space” is called the Stack; The stack is always the same size and it’s not possible to change it’s size on any way.

Heap
The Heap is also a “space” on your memory, actually it’s all the memory not allocated as a stack. So when your stack is defined, everything else can be expressed as the Heap.

Pointers
What is a pointer really? A pointer is a globally used expression to reference that your somewhat “point” to something. See the following illustration

p1
On this image we have something that we point to, let’s call A our Object. So having A as the actualy object, play with the thought that B and C isnt there, and there are no pointers to it.

This would infact mean that we had A allocated on the Stack. When does this become a problem? So play with the thought you have a really big information base such as a User Layer where you store a lot of data on each user. Then havnig a big register on all the people attending a course would take up somewhat a bigger space than we have free.

When is is an issue, we can use a pointer, to reference to this object. You can of course point to an object that you have on the stack, but that’s not. afaik, what it’s initially intended for.

So we tell our program that we want to create a Pointer, this pointer will in fact be stored on the stack, but a pointer only takes up 4 bytes so this wont be a problem.

After creating the pointer, we create the object itself and have the pointer B point to this.

Pointer, Objects s & Arrays
Assuming you know about some object orientation and how an object is constructed i will not go in to this very deeply. I.e. we have a class called Person and we want to create somewhat a register over students attending a course, what we initially want to do is create an object array, where we can store all our persons, using c++, as i will do in the following examples you would write something like this:

Person *attendingStudents = new Person[size];

Where size is equal to the max amount of students.

Running this code, the constructor of Person will be runned as many times as the size of the array attendingStudents. How is this a problem? This becomes a problem when we dont want to run the default constructor and allocate the object size  as many times as the total array size, this has too much overhead.

First of all, how does this look in memory? 

p2

On adress 0 to adress 3 wnicn means 4 bytes; every memoy block is 4 bytes; the pointer attendingStudents is allocated and on that area a 4 byte long adress is stored which in our case is 84. The size of the given Person object is not given but just play with the thought that its 4 bytes and the size is 10 this would mean the total size of the Person array would be 10 * 4 = 40 Bytes going from the address 84 to 124.

However, let’s say that the Person object takes up 4 times as much so it takes up 16 bytes per Person object, this would result in 16 * 10 = 160 bytes, going from address 84 to 244. Now, there is a big overhead if we dont use all the persons and it would be stupid to call the constructors twice.

So, how about, we just point to something that we know is a pointer, and then let this poitner take care of the rest? But we just initialize the first step?

Double pointers
Thjis is were double pointers comes in handy, look at the following code:

Person **attedningStudents = new Person*[size]:

This code is not as straight forward to look at, as the pervious one, but it basically means, 

Person **attendingStudents

  = Create a reference, to a pointer, what is a pointer? A pointer is something that will in the end point to a data type, so what we do here is saying that Point to a Pointer, this pointer will eventually have the data type Person.

Just to clearify, a pointer to an array, initially points to the first index in that array. So after creating the Pointer to a Pointer we tell it to point to a new list of Pointers, the amount of pointers to create is the same as the digit in size.

This might not make any sense, but take a look at the following

p3

Initally these pointers don’t point to anything at all so what we can do is: attendingStudents[i] which will take us to the adress 84 and then create an object on this index by doing this:

attendingStudents[i] = new Person();

Why is this method better than the one before? Well this assures that we Only have the 11 pointers which takes 4 bytes per pointer. 1 pointer on the stack, referencing 10 pointers on the stack. When does this give us overhead? This gives us a 4 byte overhead when we start creating our Persons. But the execution time saved and just given 4 bytes ovearhead per pointer, this is a preffered method by me.

Vote on HN