Website Summary Files Commits Branches @commit @diff @stats
path: root / Sem. 12 / README.md
blob: 5c13eba9bb11f6a544d94417c224035224750327 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190

# Наследяване
## Пример за наследяване

При създаване на нов клас, който има общи компоненти и поведение с вече дефиниран клас, вместо да дефинира повторно тези компоненти и поведение, можем да го обявим за наследник на вече дефинирания.

```c++
class A
{
	.
	. 
	.
public:
	void f()
	{
	.
	.
	.
	}
	.
	.
	.	
};
class B : public A
{
	.
	.
	.
}

int main()
{
	B obj;
	obj.f(); // OK!
}
 ```
 При наследяването:
 - Наследяват се член-данните и методите на основните класове
 - Получава се достъп до **някои** от наследените компоненти на основните класове


В нашия пример класът **В е наследник на класа А.** Обекти от класовете изглеждат така:

![enter image description here](https://i.ibb.co/Fshm2LJ/Untitled-Diagram.png)


След като  В е наследник на класа А, то при създаване на обект от тип В се създава обект от тип А, **който е част от обекта** от тип В.


## Видове наследяване
Някои типове наследяване в c++:

 - private (по подразбиране)
 - protected
 - public

Примери:
```c++
class A 
{
    public:
       int x;
    protected:
       int y;
    private:
       int z;
};

class B : public A
{
    // x is public
    // y is protected
    // z is not accessible from B
};

class C : protected A
{
    // x is protected
    // y is protected
    // z is not accessible from C
};

class D : private A    // 'private' is default for classes
{
    // x is private
    // y is private
    // z is not accessible from D
};
 ```

## Подаване като параметри на функции.
Класове-наследници могат да бъдат подавани като параметри на функции, които приемат обекти от базовия клас. Може да се използва функционалността само от базовия клас.

```c++
class A
{
	int a;
}
class B : public A
{
public:
	int b;
}
void f(A& obj)
{
	obj.a++;
}

int main()
{
	A obj1;
	B obj2;
	
	f(obj1); //OK!
	f(obj2); //OK!
}
 ```

## Конструктури и деструктори при наследяване.
Във всеки контструктор на класът-наследник, трябва да се оказва кой конструктор да се извика за базовия клас. Ако не оказано, ще се извика конструктора по подразбиране.

```c++
class B : public A
{
.
.
.
public:
	B(...) : A(...) //some constructor of A.
	{
	.
	.
	.
	}
}
 ```
Деструкторът на наследния клас извиква деструктора на базовия клас.


## Копиране при наследяване
При разписване на конструктора за копиране и оператора за присовяване на клас-наследник, трябва експлицитно да извикваме копиране и за базовия клас.
 ```c++
B::B(const B& other) : A(other) // (copy constructor of A (base class)
{
	copyFrom(other);
}

B& B::operator=(const B& other)
{

	if (this != &other)
	{
		A::operator=(other); //operator= of A (base class)
		free();
		copyFrom(other);
	}
	return *this;
}
 ```




## Задачи

**Задача 1:**
Реализирайте класове бар, от който ще могат да се взимат напитки (нормални и алкохолни) в определен ред. Редът ще бъде по зареждането им в бара.
**Напитката** има *име и количество (в мл)*, а **алкохолната напитка** има *име, количество и процент алкохол.*

Примерен интерфейс:
 ```c++

int main()
{
	Bar b;

	b.addDrink("Coke", 330);

	b.addDrink("Fanta", 500);

	b.addAlocoholDrink("Zagorka", 500, 5);

	b.getAcloholDrink(); // Zagorka
	
	b.getDrink() // Coke
	b.getDrink() // Fanta
}
 ```