Tip:
Highlight text to annotate it
X
C++ is an object-oriented programming language. So, what does this mean, object- oriented?
It refers to the object-oriented paradigm, meaning the method by which we can create objects of different types.
But not just different, but user defined types.
Up to this point you've been using basic, primitive types in C++. The ints, floats, bools and etc. But you've found that they have their limitations.
You can't describe adequately an entity in real life like a table or a chair or a certain kind of animal, a cat or building or whatever
using just those types. It's not enough. And you might have thought, "It'd be really nice if I'm going to model a kennel, if I could declare a dog object."
But there are no dog objects or types in C++, but now you can build such a thing.
The object-oriented paradigm allows you to create your own types in C++ and you're going to do that with
something called a class. And you've seen structs already
in these lessons and a class is very much like a struct. So here's the concept. The idea is to bundle together different data types
into one type. But, not only data types, the functionality that is going to define how these objects
are going to interact with each other and interface with other entities. We call this
encapsulation. Our basic building block is called the class and of course, your keywords are class,
public and private. So, if you look at this syntax you'll see that it's very much like a struct.
If fact, if you were to get rid of the public and private and replace the keyword class with struct, it would be exactly the same.
You are indeed defining in new class of objects in your language. The two different sections in
a class, the public and private, what goes where? The private section of the class defines an area that cannot be directly accessed
from outside of the class. That is to say the members in the private section
can't be called or accessed or changed or manipulated from any entity
outside of the class itself, like from another function, perhaps main. So, we're going to place our data members there. The member
variable are going to be in the private section of the class. That's where they are protected from inadvertent change or change that we do not
allow. That change is only going to come from the functions that are in the public section of class. So, the functions in the public section
are going to dictate how the object's state can be changed.
They're going to be the public interface. Now, it is the case that data can go in public and private.
Functions can go in public and private. However, it only makes sense to put data in the private section
that's the purpose of a class. Does it make only good sense to put functions into the public section of the class? No, it's not the case.
Quite often you have functions not only in the public but also in the private. But, the functions in the private section again can only be accessed
by the functions in the public section. I like to call the functions down in the private section as being helper functions.
For instance, you might have a public function that does a lot of stuff and you'll want to break it down into smaller tasks. You can put some of
those smaller tasks in the private section where they wouldn't normally be called by anybody outside of the class.
Let's take a look at your very first class.
Throughout this part of the semester we're going to work with a particular class as an example.
It's the class for fractions. You cannot declare a fraction in C++, there's no such thing.
Well we're going to build a class of objects we name "Fraction" so that you can indeed declare fractions now and work with fractions. So,
again we have our class and the name of the type which is "Fraction". Now, I want to give you this caveat at this point. The fraction class that
I'm going to build over the next several lessons is not a fraction class that I personally would build if I was going to use it. The functions
that I'm going to use to demonstrate classes in this particular example I've put in here not because
I think it would really be good for fraction class, but because they demonstrate the principles that I'm trying to show you.
Okay, so here is our public section and the member functions and we have four of them. And notice that these are the prototypes for the
functions. I have my return type, I have my name and because of the parenthesis, we know that
that is a function. I've got four functions, as I said. "void readin();" what that's going to do is to allow the user to read information into the
member variables of the object. We have a "print" function which is going to print out the information that's contained in the
data. We have a "reciprocal" function that is going to return a fraction and we have an "unreduce" function
which takes an integer and returns nothing and what it's going to do is change the object by
multiplying "Numerator" and "Denominator" by the same value. And of course in the private section we have the member data of
this class of objects. Of course a fraction is made up of a numerator and a denominator. And just like with a struct, you only want to put it in the
data list elements that describe the state of this kind of object.
One detail that might come in handy: in a class anything inside the curly braces that is not otherwise designated as public or private is
private by default. These two ways of writing this class are exactly the same. It's much preferable I think to put the "private", it makes it clearer.
Okay, so how do we put all this together?
A class definition, what I call a class definition and what some would call a class
declaration is this, just like a strut. And it's best to put it in its very own header named appropriately. So, in "fraction.h" I have my class "fraction"
and I wouldn't want to put anything else in this header accept any constants that might be associated with fractions.
In this case there are none. This would be the only thing in that header.
The idea is that you can pick this up and move it from project to project. Now we're also going to have an associated implementation file, a cpp
file, a faction.cpp, which is going to contain the definitions of
these member functions right here. They're not defined here. You don't see those definitions and in fact I'm not going to go over that in this lesson.
What I want to show you is how this object is going to be used.
Let's go to our main here, and in our main function we want to "#include" the fraction header so that the
compiler knows what a fraction is. So, here in this line, I have
declared two fractions f and g. Again it's just like any other declaration. The type is fraction the objects are
named f and g. Our next line of code, is this legal? No, it's not legal. Okay, this will not compile.
Why not? Why won't this compile? Why can I not change the numerator of my fraction?
And this is how I would do it if it was a struct. Alright, I use the
dot operator. I say f, this object, its numerator, its member variable (as
indicated by the "m_") its member variable numerator I want to set that equal to seven.
Why can't I do that? Well, remember it's in the private section of the class. This is not directly accessible in any function that is not a member
function of the class. Well, main is not a member function of the class and that's what I'm trying to do
in main. All I can do is have f call its "readin" function, it can call its "print" function, it can call its
"unreduce" function, but it cannot directly changemember variables. And so, that's the basis of the object-oriented paradigm. In the next
lesson, I'm going to show you how to define those functions, how they work and the whole concept
of a calling-object. If we go back just a step, here in these three lines, f calls its "readin" function,
"print" function and "unreduce" function. F is called the calling object. It's the object that's calling
those member functions. So, we'll take a look at the details in the next lesson.