Before we begin learning the new advanced features of C++, we need to talk about some of the principles of good class design. Why is a good class design important? That is because without good class design, the ability to extend software functionality or add new features to it is severely diminished. So let's talk about some of the principles that are most useful and let's start with the principle called DRY. DRY is an acronym that stands for do not repeat yourself, which means that you should write code to do something or describe something once and only once. So what exactly does that mean? Let's take a look at an example. You have a class called DoNotRepeat, which is highlighted. And that class has some variables, some member variables called integer_var, double_var and string_var. It also has functions to set those variables and also retrieve their values. Now let's consider the another class, called this class Repeated. Take a look at it has very similar layout. It has a similar member variables called integer_var, double_var, string_var and has similar interface functions to set those variables and retrieve of some of their values, but also to calculate some other value based on those values. So if you look at these 2 classes and you will understand that if you're need to change a feature, that is the same between them, you will probably need to make changes twice. You will need to change the DoNotRepeat and you will then also need to change Repeated, which is of course practically possible, but very bad idea because changes of the code that have to be repeated 2, 3, 4 times is a very good way to introduce bugs in your program. So C++ provides you with a mechanism that will allow you to write the code that is common between the 2 classes once and only once, which is called inheritance. And we will be talking about it in some of the sections to follow. Another principle that we need to talk about is encapsulation. And that is principle is actually very important. Encapsulation is a principle by which object's properties is protected from direct access by outside functions or classes. This is not the only thing that encapsulation necessitates. Properly encapsulated objects have very narrow interface, which means that an outside user can only do few things with the objects, but the number of components and internal functions inside the object can be large and they could do some things on their own, but you cannot perform those functions without accessing the interface of the encapsulating object. For this example, let's take a look at an object class called Mixer, which describes a standing kitchen mixer. In my example, I'm describing a Kitchen Aid mixer and as you can see, it has a very simple interface. You can start it, stop it, mix. You can remove the cup, you can install the cup, you can unlock the mixer, lock the mixer, and you can also raise the mixer. Those are the only functions that you can perform on the properly encapsulated object. You also know that the mixer contains gears, motor, controller, and a few other components, but you have no access to them as a normal user of the object. You know these exist individually. They're of very little interest to you and you have no need to control them or have the function of controlling them except through the object. The next principle that we will look at is called a single responsibility principle. This is a fancy way of saying that class should be responsible for one thing and one thing only. If a class, for example, is responsible for describing a sales order, it should not be responsible for saving the information of that sales order to the database nor should it be responsible for converting itself to another format like XML. Why is that not a good idea? Well, it actually is very simple. Itself to the database, for example, the object needs to have the database information. So if you have many sales order, each one needs to have a copy of the database information, which is prone to errors and makes the code really confusing to read and very difficult to maintain. So unless absolutely necessary, dependencies like these should be avoided. The last principle that we will talk about in this section is called the open-closed principle. The principle states that the class should be open to extension, but close to modification. So what exactly does that mean? Let's take a look at something for rule validation. You have a class called RuleValidation, which has an interface method called validate rule to which you put a rule object, which you can describe by yourself. And then you have the validation logic in the method and it means that every time you add a new rule or a new type of validation, you will have to change the RuleValidation class to accommodate the new functionality. A better way to do this would be to have a class called ValidateRule, which will have a public function called validate. So for every type of validation that you want, you will create an object of this class. And you can extend this again by using inheritance. You can extend it for, provide a specific types of validation. And then you can actually have rule validation, have a set of validate rules objects, which validate we'll actually call in succession until it gets that the rule is valid, or it will get the failure on all of them. This way, the rule validation object doesn't have to change very much to accommodate new validate rules. The only thing that you will need to add is a function called addRuleValidator, which will take the validate rule object, and will add them to the validation set. Add validate rule. And then you can very simply add many validations as many validations as you'd like, which is exactly how it is described in the open-closed principle.