Classes and Objects
The course is part of this learning path
Ever wondered how they maintain all the data and behaviors for the items in your inventory in a video game? Or maybe you've thought about how super-complex complex systems like banking systems, store management software, automotive digital diagnostic systems and tons of other applications were built? There's often a good chance that many of these applications use some form of Object-Oriented Programming. In this course, we look at Object-Oriented Programming, focusing on objects and classes.
- Understand how classes are designed and constructed and how objects are created from them
- Explore both the data members and member functions from which we build classes
- Learn how to instantiate classes as objects
- Learn how to use a rectangle class and a book class together and test them out
- Beginner coders, new to C++
- Developers looking to upskill by adding C++ to their CV
- College students and anyone studying C++
To get the most out of this course, you should have a basic understanding of the fundamentals of C++.
Since the beginning of this section, we've learned a lot about the syntax and concepts used with classes and objects. Everything from separate compilation and applying const to member functions to constructors and destructures which were covered in the previous lecture. As a quick review, say the names of the three primary principles of object-oriented programming out loud. So what are they? That's right. Encapsulation, inheritance and polymorphism. Good job. Repeat those multiple times as you begin and end your studies for the day. We have focused heavily on encapsulation, where we combine data and behaviors in the form of the data members also called fields and the member functions also called methods in single entities that we call objects. We use classes as the blueprints for these objects. We continue practicing these newfound skills and terminology in the remaining lectures by not so much learning new material as we are going to be solidifying our current knowledge by creating some more classes. In this lecture, we're going to take what we've learned and apply it to the construction of a Rectangle class. First, let's consider what we need to represent a rectangle. What you see right now is a UML class diagram. UML stands for Unified Modeling Language. There are a wide variety of UML diagrams used to help software engineers to plan and design software as part of the software process and they are not specific to C++. The word model seems very technical, but it's not anything difficult to understand. A model is, in essence, a simplified version of whatever we're trying to represent. UML helps software developers with the modeling process. UML class diagrams are an extremely popular tool used by many software developers who want to create different classes or design a system in which there are many interacting classes. Sometimes you may even have a software team leader, give you a set of UML class diagrams and some additional information and expect you to code it in a particular language such as C++. UML class diagrams are divided into three sections. At the top of the UML diagram, we have the name of the class. In the middle section, you list any of the data members or fields, and in the bottom section you list the member functions or methods. Remember that UML class diagrams use their own syntax and that this syntax doesn't match C + + exactly. For example, the identifiers always come first and they are followed by a colon followed by the data types or return types of the data members or member functions respectively. You might have also noticed that the parameters are listed in the identifier colon type order. Also notice the minus and plus symbols in front of the identifiers. The two data members, length and width, are both private. So, that's why there's a minus sign in front of them. The member functions are all public. So, that's why they all have a plus sign in front of them. Make a note that the data always goes in the middle section and the methods always go in the bottom section. Their access modifiers such as public or private do not affect this aspect of UML class diagrams. Now, taking what we know about the Rectangle class from the UML class diagram, let's write the appropriate code. First, we will need to create a new project in visual studio that we're going to name Rectangle fun. Create new project, Empty project. We will call it Rectanglefun. And Create. So, we need to create three different files. Main.cpp will be our file that will house the main function. Rectangle.h will be the specification or header file for our Rectangle class. And Rectangle.cpp will be the implementation file for our Rectangle class. So, let's create those three now. So, we've got the source file, new item and that would be called main.cpp as we always have created. While I'm in the area, I'm going to create the Rectangle.cpp. And the header file, I'm going to create the header Rectangle.h. Awesome. So, now we have our three files. Now we have to fill in the skeleton of main as usual. And this time, I'm going to make sure that I include Rectangle.h, notice the double quotes, using name space standard. Okay, there we go. And let's turn our attention now to the specification file Rectangle.h and fill that in. Instead of pragma once, we will use the include guards that we learned about before. And again RECTANGLE_H define RECTANGLE_H and endif. Okay, so, class Rectangle and we have public section and a private section here, okay. And I need to get that right there, okay. So, the public and private sections. Now we know that to represent a rectangle, even from our UML diagrams, all we need is the length and the width. For the public, we're going to create a constructor, no argument constructor. We will also have a parameterized constructor that takes a length and width. We will also have getLength. And since this does not modify the internal data of the rectangle, we're going to make it const. And getWidth const. And also void setLength. And that one isn't const because it does modify the internal data. setLength and setWidth, and of course, area. An area performs a calculation based on the length and the width but it does not modify the internal data, so that can be const as well. That's pretty awesome because except for remembering the include guards and to put the const keyword after the methods that don't change the data fields of the object, the specification file is actually very close to the UML class diagram, isn't it? So, now for the actual implementation. So, let's go to the implementation file. And we're going to include Rectangle.h. And we are now going to... Let's say, for the no arc constructor, we're going to assume that we want to create a unit square. So, that's one in which the length and the width of the rectangle is one each. So, we're going to say, Rectangle::Rectangle. So, this is going to be my constructor. And I can say this length equals 1.0, this length equal... or width rather, sorry, width equals 1.0, so that makes the unit square. The next thing, and I could of course, copy these over from the .h file, which I will probably do in the future, but for right now we're just taking it slow. So, you can see what I'm doing. That gives you time. So, we have rectangle length, rectangle width. This length is equal to the length that's passed down. This width is the width that's passed down. And now we have Rectangle, we have here getLength. const, that just returns the length. And then Rectangle getWidth, const return the width. Good. All right, so now we want to have these setters. So, we have void Rectangle setLength that takes the length. And then before we fill it in, I'll set the set width up as well. Okay, now we can fill these two in. So, what are we going to do? This time we need to use this because we have parameters that caused so called shadowing, which we'll talk about. This width equals width, and then finally double Rectangle. This is probably the most complicated of all of them and it's not really that hard, right? So, how do you get the area of a Rectangle? That's the length times the width. That's all we have to do. The reason we don't have to put this in front of here is because there's no parameter that's overshadowing the name of the private data which happens to also be length and width respectively. So, we have both our header file and our definitions filled out now for the Rectangle class and its data members or fields and member functions or methods. Again, those are synonyms for one another. Now it's time to see how to actually use the rectangle class and create instances of the class, that is, objects. So, inside of main, we're going to say rectangle like we did with our house, rectangle r1 and then rectangle r2 and this time it's going to be 5.0, 2.0. Alright, so obviously the r1 will call the no arg constructor and then this one since it takes two doubles, that will call the constructor that takes two doubles, neat. Print out r1's area, r1.area and then r2 area, r2.area. And now we want to maybe change the length and the width of r1, so 22x12 and now I'm going to say r1 length is now, r1.getLength and then r1 width is now getWidth. Alright. So, the length is now length, width is now width, and then r1 area is now r1.area and there we go, good. Alright, so let's run it. Debug, start without debugging. Alright. So, initially the area of r1 is 1 and if you think about it, that's what the constructor that we created does, it creates a unit square. So, that would be a one length one width, so that's 1 times 1 and that's 1. And then we created another rectangle r2 which is a 5 by 2, so that's 10. So, that's the correct area. And then what we do is we have the r1 length is 22, r1 width is 12 so the area is then 264 and there's again the missing space. So, formatting this is another reason you test because formatting is sometimes a problem. So, there we go. That looks a little bit prettier. So, 264 and you can of course verify that 22 times 12 is indeed 264. Good. So, that's awesome work. In professional environments, you definitely want to do very thorough testing but we've done a pretty decent job of making sure that each of our constructors are area method and the setter and getter methods work well. Now before we move onto the next lecture, you guessed it? I have a challenge for you. I want you to modify our current rectangle fun project and I want you to add a perimeter method. Not parameter, a perimeter method that uses the length and the width to calculate the perimeter of the rectangle. In case you don't remember, the perimeter of the rectangle is the sum of the measurements of the four sides of the rectangle. In other words, it's 2 times the length plus 2 times the width. So, write the perimeter method and don't forget to modify both the rectangle.h and rectangle.cpp files and also to test your new method out by calling it on the r1 and r2 objects from inside of main. So, pause the video and give it your best shot. Come back when you're done or if you need some help. Did you complete the challenge? I hope you did. Regardless, let's do it together and you can see my solution. So, I'm going to add the perimeter method. So, write here double perimeter() const. There we go. And this time I'm just going to copy that and go over here into my .cpp file. Give it a body and of course to make it a method rather than a global function, we need to add the name of the class and the scope resolution operator or the two colons. And how do we calculate this? Well, you could do it this way, return 2 * length + 2 * width. Alternatively, if you did return 2 * and then (length + width), that is also acceptable. Or even if you store it in a variable and then return it, that's fine too. Now we have to test this out to make sure it works. So, in main, we have to call it. So, at the very end, I'm going to say r1 perimeter is r1., and look here, we now have the perimeter method. And now, r2 perimeter is r2.perimeter. There we go, and we will run it again. So, the last two values we get should be the perimeter and they are. So, r1 perimeter is 68, r2 perimeter is 14. So, by the time we called them there, the perimeter we had 22 and 12, so if you have two 22s that's 44, two 12 is 24. So, 44 plus 24 is indeed 68. And then r2 is a 5 by 2. So, that means two of the sides are 5, that's 10 and two of the sides are 2, that's 4. So, that's 14. Good work everyone. Let's go onto the next lecture where we'll be making a book class to further test our skills. Let's see how that goes. I'll see you there.
John has a Ph.D. in Computer Science and is a professional software engineer and consultant, as well as a computer science university professor and department chair.