[Road to DL Engineer] C++ Tutorial ~Object Oriented~

こちらの投稿では下記チュートリアルの目次をご覧いただくと記載のある、Object Orientedのパートを扱うものとします！
それ以降は別の記事にて記載をいたします。

Bear in mind that this post aims to master C++ for beginners.
And most probably containing some mistakes, so please kindly notice me!

Tutorial Link: https://www.tutorialspoint.com/cplusplus/cpp_overview.htm
推薦していただいた参考サイト：http://www.learncpp.com/

Previous post [~Basics~](https://qiita.com/Rowing0914/items/aee5e023d35027682f02)
Next post [~Advanced~](https://qiita.com/Rowing0914/items/9dbf7acf3bfb9b413cb6)

## Contents
1. Classes and Objects
2. Inheritances
3. Overloading (Operator and Functions)
4. Polymorphism
5. Abstraction
6. Encapsulation
7. Interface

## 1. Classes and Objects
When you define a class, implicitly you define a blueprint for a datatype.
However it doesn't actually define any kind of data, hence there is no memory action.

**public** gives us the access attributes of the members of the class.

```c++
#include <iostream>

using namespace std;

class Box{
public:
	double length;
	double breadth;
	double height;
};

int main(){
	Box Box1;
	Box Box2;

	double volume = 0.0;

	// box 1 specification
   Box1.height = 5.0; 
   Box1.length = 6.0; 
   Box1.breadth = 7.0;

   // box 2 specification
   Box2.height = 10.0;
   Box2.length = 12.0;
   Box2.breadth = 13.0;

   volume = Box1.height * Box1.length *Box1.breadth;
   cout << "Volume of Box1 : " << volume <<endl;

   // volume of box 2
   volume = Box2.height * Box2.length * Box2.breadth;
   cout << "Volume of Box2 : " << volume <<endl;
   return 0;
}

#output
Volume of Box1 : 210
Volume of Box2 : 1560
``` 

## 2. Inheritances
It is one of the most important concept in C++, and this enhances us to define a class in terms of another class, which improves our efficiency.

>
The idea of inheritance implements the is a relationship. For example, mammal IS-A animal, dog IS-A mammal hence dog IS-A animal as well and so on.

Image
![inheritance.png](https://qiita-image-store.s3.amazonaws.com/0/240801/618373cd-c8e6-3f61-b3f7-55a93cab3e11.png)

**Accessibility of Inheritance**
![Screen Shot 2018-03-29 at 19.26.04.png](https://qiita-image-store.s3.amazonaws.com/0/240801/277a971e-6a4f-aded-1608-f863b98026e5.png)

```c++
#include <iostream>
 
using namespace std;

// Base class Shape
class Shape {
   public:
      void setWidth(int w) {
         width = w;
      }
      void setHeight(int h) {
         height = h;
      }
      
   protected:
      int width;
      int height;
};

// Base class PaintCost
class PaintCost {
   public:
      int getCost(int area) {
         return area * 70;
      }
};

// Derived class
class Rectangle: public Shape, public PaintCost {
   public:
      int getArea() {
         return (width * height); 
      }
};

int main(void) {
   Rectangle Rect;
   int area;
 
   Rect.setWidth(5);
   Rect.setHeight(7);

   area = Rect.getArea();
   
   // Print the area of the object.
   cout << "Total area: " << Rect.getArea() << endl;

   // Print the total cost of painting
   cout << "Total paint cost: $" << Rect.getCost(area) << endl;

   return 0;
}

#output
Total area: 35
Total paint cost: $2450
```
## 3. Overloading (Operator and Functions)

```C++
#include <iostream>
using namespace std;

class printData{
public:
	void print(int i){
		cout << "Printing int: " << i << endl;
	}
	void print(double d){
		cout << "Printing double: " << d << endl;
	}
	void print(string s){
		cout << "Printing string: " << s << endl;
	}
};

int main(void){
	printData pd;
	pd.print(34);
	pd.print(3.134);
	pd.print("Hello!");
}

#output
Printing int: 34
Printing double: 3.134
Printing string: Hello!
```

**Overloading operators**
C++ lets us modify even their operators!!

```c++
#include <iostream>

using namespace std;

class Box{
public:
	double getVolume(void){
		return length * breadth * height;
	}
	void setLength(double len){
		length = len;
	}
	void setBreadth(double bre){
		breadth = bre;
	}
	void setHeight(double hei){
		height = hei;
	}

	Box operator+(const Box& b){
		Box box;
		box.length = this->length + b.length;
		box.breadth = this->breadth + b.breadth;
		box.height = this->height + b.height;
		return box;
	}
private:
	double length;
	double height;
	double breadth;
};

int main(void){
	Box Box1;
	Box Box2;
	Box Box3;

	double volume = 0.0;

	   // box 1 specification
   Box1.setLength(6.0); 
   Box1.setBreadth(7.0); 
   Box1.setHeight(5.0);
 
   // box 2 specification
   Box2.setLength(12.0); 
   Box2.setBreadth(13.0); 
   Box2.setHeight(10.0);
 
   // volume of box 1
   volume = Box1.getVolume();
   cout << "Volume of Box1 : " << volume <<endl;
 
   // volume of box 2
   volume = Box2.getVolume();
   cout << "Volume of Box2 : " << volume <<endl;

   // Add two object as follows:
   Box3 = Box1 + Box2;

   // volume of box 3
   volume = Box3.getVolume();
   cout << "Volume of Box3 : " << volume <<endl;

   return 0;
}

#output
Volume of Box1 : 210
Volume of Box2 : 1560
Volume of Box3 : 5400
```

## 4. Polymorphism
Polymorphism allows us to define the function with the same name, but different actions.
Bear in mind that if we don't put "virtual" keyword before area(), then the output becomes just "Parent class area: ".
this is called early binding and happens while the compiler is reading int area() in parental class, it also tries to initialise area() of Rectangle/Triangle. Hence the conflict arise in it.

```c++
#include <iostream>

using namespace std;

class Shape{
protected:
	int width, height;

public:
	Shape(int a = 0, int b = 0){
		width = a;
		height = b;
	}
	virtual int area(){
		cout << "Parent class area: " << endl;
		return 0;
	}
};

class Rectangle: public Shape{
public:
	Rectangle(int a = 0, int b = 0){}
		int area(){
			cout << "Rectangle class area: " << endl;
			return (width*height);
		}
};

class Triangle: public Shape{
public:
	Triangle(int a = 0, int b = 0){}
	int area() {
		cout << "Triangle class area: " << endl;
		return (width*height/2);
	}
};

int main(){
	Shape *shape;
	cout << "shape is: " << shape << endl;
	Rectangle rec(10,7);
	Triangle tri(10,5);
	shape = &rec;
	cout << "shape is: " << shape << endl;
	shape->area();
	shape = &tri;
	cout << "shape is: " << shape << endl;
	shape->area();
	return 0;
}

#output
shape is: 0x117d56248
shape is: 0x7ffee546b1c0
Rectangle class area: 
shape is: 0x7ffee546b1b0
Triangle class area: 
```
**protected** gives the access to its child/sub-classes.
So in this code, Rectangle/Triangle can touch width, height.

## 5. Abstraction
Data abstraction is a programming (and design) technique that relies on the separation of interface and implementation.

```c++
#include <iostream>
using namespace std;

class Adder {
   public:
      // constructor
      Adder(int i = 0) {
         total = i;
      }
      
      // interface to outside world
      void addNum(int number) {
         total += number;
      }
      
      // interface to outside world
      int getTotal() {
         return total;
      };
      
   private:
      // hidden data from outside world
      int total;
};

int main() {
   Adder a;
   
   a.addNum(10);
   a.addNum(20);
   a.addNum(30);

   cout << "Total " << a.getTotal() <<endl;
   return 0;
}

#output
Total 60
```

## 6. Encapsulation
Data encapsulation is a mechanism of bundling the data, and the functions that use them and data abstraction is a mechanism of exposing only the interfaces and hiding the implementation details from the user.

```c++
#include <iostream>
using namespace std;

class Adder{
public:
	Adder(int i = 0){
		total = i;
	}
	void addNum(int number){
		total += number;
	}
	int getTotal(){
		return total;
	};

private:
	int total;
};

int main(){
	Adder a;
	cout << "total: " << a.getTotal() << endl;
	a.addNum(1);
	cout << "total: " << a.getTotal() << endl;
	a.addNum(2);
	cout << "total: " << a.getTotal() << endl;
	a.addNum(3);
	cout << "total: " << a.getTotal() << endl;
	return 0;
}

#output
otal: 0
total: 1
total: 3
total: 6
```

## 7. Interface
The C++ interfaces are implemented using abstract classes and these abstract classes should not be confused with data abstraction which is a concept of keeping implementation details separate from associated data.

```c++
#include <iostream>

using namespace std;

class Shape{
public:
	virtual int getArea() = 0;
	void setWidth(int w){ width = w; }
	void setHeight(int h){ height = h; }
protected:
	int width;
	int height;
};

class Rectangle: public Shape{
public:
	int getArea(){
		return (width*height);
	}
};

class Triangle: public Shape{
public:
	int getArea(){
		return (width*height)/2;
	}
};

int main(void ){
	Rectangle Rect;
	Triangle Tri;

	Rect.setHeight(5);
	Rect.setWidth(4);
	cout << "Total Rectangle area: " << Rect.getArea() << endl;

	Tri.setWidth(5);
	Tri.setHeight(7);
   
	// Print the area of the object.
	cout << "Total Triangle area: " << Tri.getArea() << endl; 
	return 0;
}

#output
Total Rectangle area: 20
Total Triangle area: 17
```