This shows you the differences between two versions of the page.
poo-is:laboratoare:08 [2020/09/29 14:52] eduard.ciurezu [Destructori virtuali puri/abstracti] |
poo-is:laboratoare:08 [2020/10/03 11:27] (current) alexandru.ionita99 |
||
---|---|---|---|
Line 1: | Line 1: | ||
- | ===== Laboratorul 08: Mostenire multipla. Clase si functii abstracte. Interfete ===== | + | ======= Laboratorul 08: Mostenire multipla. Clase si functii abstracte. Interfete ======= |
In cadrul acestui laborator, vom discuta despre **mostenirea multipla** si ambiguitatile care pot aparea o data cu aceasta, despre **clasele si functiile abstracte** si despre **interfete**, cu ajutorul carora vom reusi sa aprofundam cunostintele legate de derivarea claselor si suprascrierea metodelor acestora. | In cadrul acestui laborator, vom discuta despre **mostenirea multipla** si ambiguitatile care pot aparea o data cu aceasta, despre **clasele si functiile abstracte** si despre **interfete**, cu ajutorul carora vom reusi sa aprofundam cunostintele legate de derivarea claselor si suprascrierea metodelor acestora. | ||
Line 7: | Line 7: | ||
* Separate Interface and Implementation (pag. 264-265) | * Separate Interface and Implementation (pag. 264-265) | ||
- | ====== Mostenire Multipla ====== | + | ===== 1. Mostenire Multipla ===== |
Spre deosebire de multe alte limbaje de programare orientate-obiect, C++ permite **mostenirea multipla** (o clasa poate fi derivata din mai multe clase de baza). | Spre deosebire de multe alte limbaje de programare orientate-obiect, C++ permite **mostenirea multipla** (o clasa poate fi derivata din mai multe clase de baza). | ||
<note>In acest caz, la declararea clasei derivate nu se specifica o singura clasa de baza, ci o succesiune de clase de baza, separate prin virgula, avand in fata specificatorii de acces.</note> | <note>In acest caz, la declararea clasei derivate nu se specifica o singura clasa de baza, ci o succesiune de clase de baza, separate prin virgula, avand in fata specificatorii de acces.</note> | ||
<code>class C:public A, public B</code> | <code>class C:public A, public B</code> | ||
- | <note>In candrul mostenirii multiple, **constructorii** claselor de baza vor fi apelati in ordinea enumerarii, iar **destructorii** vor fi apelati in ordine inversa.</note> | + | <note>In cadrul mostenirii multiple, **constructorii** claselor de baza vor fi apelati in ordinea enumerarii, iar **destructorii** vor fi apelati in ordine inversa.</note> |
- | ===== Problema Diamantului ===== | + | ==== 1.1. Problema Diamantului ==== |
Desi mostenirea multipla pare a fi un procedeu util, aceasta poate duce la multe ambiguitati, cea mai mare dintre acestea fiind **Problema Diamantului** (numita si **“death diamond”**). Sa consideram urmatoarea ierarhie de clase: | Desi mostenirea multipla pare a fi un procedeu util, aceasta poate duce la multe ambiguitati, cea mai mare dintre acestea fiind **Problema Diamantului** (numita si **“death diamond”**). Sa consideram urmatoarea ierarhie de clase: | ||
Line 32: | Line 32: | ||
<note>Pentru a se crea un obiect de tip **Snake**, se vor apela constructorii claselor **Animal** and **Reptile**, dar se va apela o singura data constructorul clasei **LivingThing**, astfel **Snake** va avea o singura instanta a clasei **LivingThing**.</note> | <note>Pentru a se crea un obiect de tip **Snake**, se vor apela constructorii claselor **Animal** and **Reptile**, dar se va apela o singura data constructorul clasei **LivingThing**, astfel **Snake** va avea o singura instanta a clasei **LivingThing**.</note> | ||
- | ====== Clase si Functii Abstracte ====== | + | ===== 2. Clase si Functii Abstracte ===== |
O metoda virtuala se numeste **abstracta (pura)** daca nu are implementare: | O metoda virtuala se numeste **abstracta (pura)** daca nu are implementare: | ||
Line 68: | Line 68: | ||
<note important> | <note important> | ||
- | * Functiile abstracte sunt folosite in cazul in care metoda nu are o implementare in clasa de baza, insa dorim sa o declaram virtuala. | + | * **Functiile abstracte** sunt folosite in cazul in care metoda nu are o implementare posibila in clasa de baza, insa dorim sa o declaram virtuala. |
- | * Nu se pot instantia obiecte de tipul unei clase abstracte, **DAR** se pot declara pointeri de acel tip. | + | * **NU** se pot instantia obiecte de tipul unei clase abstracte, **DAR** se pot declara pointeri de acel tip. |
- | * Suntem obligati, ca eventual, sa implementam functia intr-o clasa derivata, altfel, si aceasta clasa derivata o sa fie tot abstracta. | + | * Suntem obligati, ca eventual, sa implementam functia intr-o clasa derivata, altfel, si aceasta clasa derivata o sa fie tot **abstracta**. |
</note> | </note> | ||
- | ====== Interfete ====== | + | ===== 3. Interfete ===== |
<note>O clasa fara atribute si cu toate metodele abstracte se numeste **interfata**.</note> | <note>O clasa fara atribute si cu toate metodele abstracte se numeste **interfata**.</note> | ||
Line 111: | Line 111: | ||
</code> | </code> | ||
- | <note important>Interfetele pot fi folosite pentru a declara liste neomogene de obiecte diferite. | + | <note tip>**Interfetele** pot fi folosite pentru a declara liste neomogene de obiecte diferite. |
- | Spre exemplu, daca avem obiecte de tip Student si obiecte de tip Angajat, putem declara o interfata pe care cele doua tipuri sa o mosteneasca. Astfel putem declara o lista de angajati si studenti. | + | Spre exemplu, daca avem obiecte de tip **Student** si obiecte de tip **Angajat**, putem declara o **interfata** pe care cele doua tipuri sa o mosteneasca. Astfel putem declara o lista de angajati si studenti. |
</note> | </note> | ||
- | |||
- | ===== Destructori virtuali puri/abstracti ===== | ||
<note important>Este absolut necesara declararea **destructorilor virtuali abstracti**! | <note important>Este absolut necesara declararea **destructorilor virtuali abstracti**! | ||
In cazul in care destructorul nu este adaugat si implementat, destructorul clasei derivate nu va putea fi apelat niciodata.</note> | In cazul in care destructorul nu este adaugat si implementat, destructorul clasei derivate nu va putea fi apelat niciodata.</note> | ||
+ | |||
+ | == Exemplu: == | ||
+ | |||
+ | |||
+ | <code c++> | ||
+ | //Interfata | ||
+ | class BazaAbstracta { | ||
+ | public: | ||
+ | virtual ~BazaAbstracta() = 0; //Destructor virtual | ||
+ | }; | ||
+ | |||
+ | //Implementare destructor virtual | ||
+ | BazaAbstracta::~BazaAbstracta() {} | ||
+ | |||
+ | //Clasa derivata | ||
+ | class Derivata: public BazaAbstracta { | ||
+ | //Membrii, metode | ||
+ | }; | ||
+ | </code> | ||
+ |