This is an old revision of the document!
În urma parcurgerii acestui laborator studentul va:
Studiați codul de mai jos.
|
|
Observăm două bucăți din cod în mod special:
Complex::Complex(double re, double im);
Linia de mai sus nu are tip returnat, spre deosebire de celelalte linii. Acesta este constructorul clasei, care este apelat în momentul alocării unui obiect.
Ce operații sunt uzuale în constructor?
A doua bucată observată este:
Complex numar(2, 3);
Până acum nu ați mai alocat astfel structurile. Ce se întâmplă în spate este exact ceea ce intuiți: este apelat constructorul obiectului și se execută instrucțiunile acestuia pentru variabila numar (reprezentată ca pointer prin this, direct în interiorul constructorului).
În constructorul definit mai sus, tot ceea ce se întâmplă este să se inițializeze membri. Pentru asta, C++ vă pune la dispoziție o sintaxă simplă:
Complex::Complex(double real, double imaginar) : re(real), im(imaginar) { }
Cei doi constructori sunt identici ca funcționalitate.
Reprezintă un tip de constructor special care se folosește când se dorește/este necesară o copie a unui obiect existent. Dacă nu este declarat, se va genera unul default de către compilator.
Poate avea unul din următoarele prototipuri
1) Apel explicit
MyClass m; MyClass x = MyClass(m); /* apel explicit al copy-constructor-ului */
2) Transfer prin valoare ca argument într-o funcție
void f(MyClass obj); ... MyClass o; f(o); /* se apelează copy-constructor */
3) Transfer prin valoare ca return al unei funcții
MyClass f() { MyClass a; return a; /* se apelează copy-constructor */ }
4) La inițializarea unei variabile declarate pe aceeași linie
MyClass m; MyClass x = m; /* se apelează copy-constructor */
Reprezintă un concept de must do pentru C++. Astfel:
Explicație: dacă funcționalitatea vreunuia dintre cei 3 se vrea mai specială decât cea oferită default, atunci mai mult ca sigur se dorește schimbarea funcționalității default și pentru ceilalți 2 rămași.
class Complex { private: int re; int im; public: Complex() { re = 0; im = 0; printf("constructor default\n"); } Complex(const Complex& c) { re = c.re; im = c.im; printf("copy contructor\n"); } void operator=(const Complex& c) { re = c.re; im = c.im; printf("assignment operator\n"); } };
Așa cum probabil ați observat, constructorul este apelat în mod explicit de către voi. Destructorul însă, în cazul de mai sus, este apelat implicit la terminarea blocului care realizează dealocărea automată a obiectului.
Un destructor nu are parametri și se declară în interiorul clasei astfel:
~Complex();
Dacă în constructor sau în interiorul clasei ați fi alocat memorie, cel mai probabil în destructor ați fi făcut curat și ați fi apelat free pe membrul respectiv.