Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
POO - Curs Doc-1.doc
Скачиваний:
0
Добавлен:
01.07.2025
Размер:
868.86 Кб
Скачать

§12. Constructor de copiere

Orice clasă chiar dacă nu are un constructor de copiere definit explicit, are unul care este un constructor de copiere creat implicit de către compilator. Constructorul de copiere implicit face copierea binar cu binar a informaţiei dintr-un obiect creând un obiect nou. Dar un astfel de mecanism de obţinere a obiectelor-copii poate duce la erori grave. Acest fapt se poate întâmpla când clasa, în baza căreia sunt create obiecte, conţine pointeri care punctează la careva fragmente de memorie alocate dinamic. Dacă vor fi create copii ale unui obiect de acest tip prin metoda constructorului de copiere implicit, atunci vor exista mai multe obiecte care au asociate acelaşi fragment de memorie:

Dacă unul dintre aceste obiecte va fi nimicit, fragmentul de memorie asociat va fi eliberat şi atunci obiectele rămase vor arăta la un fragment de memorie inexistent. Dacă vor fi efectuate operaţii în cadrul acestui fragment de memorie, ele vor genera erori.

Constructorul de copiere este apelat în următoarele situaţii posibile:

  1. Definirea unei variabile de tip obiect, iniţializând-o în baza unui obiect existent;

  2. Transmiterea de obiecte în calitate de parametri reali ai unei funcţii care are parametri fictivi de tip obiect. Fiecare obiect va genera o copie, creată cu ajutorul constructorului de copiere.

  3. Funcţiile care returnează o valoare de tip obiect în momentul returnării valorii creează o copie a obiectului.

Erori de tipul celei descrise anterior pot fi obţinute uşor, de exemplu, la transmiterea unui obiect în calitate de parametru real la apelarea unei funcţii. Va fi creat un obiect-copie, care la terminarea funcţiei va fi nimicit. Astfel, obiectul transmis în calitate de parametru real va fi afectat serios.

Pentru a evita asemenea erori trebuie de definit în cadrul clasei un constructor de copiere, care ar schimba scenariul de lucru al constructorului de copiere implicit. Şi anume, obiectul-copie ar trebui să-şi aibă propria memorie asociată, care conţine informaţie similară cu memoria asociată obiectului, în baza căruia este creată copia:

Un constructor de copiere are un parametru fictiv de tip referinţă şi este descris în felul următor:

class nume_cl

{

. . .

nume_cl(nume_cl &ob);

. . .

};

iar implementarea lui poate fi descrisă astfel:

nume_cl::nume_cl(nume_cl &ob)

{

// instructiuni

}

Exemplu:

class tablou

{

int *date;

int dim;

public:

tablou(int d, int val);

tablou(tablou &t);

~tablou();

void modificaTablou();

void afisare();

};

//-----------------

tablou::talbou(int d, int val)

{

date=new int[d];

if(date!=NULL)

{

dim=d;

for(int i=0;i<dim;i++) date[i]=val;

}

else

dim=0;

}

//-----------------

tablou::tablou(tablou &t)

{

dim=t.dim;

date=new int[dim];

for(int i=0;i<dim;i++) date[i]=t.date[i];

}

//-----------------

tabou::~tablou()

{

delete[] date;

}

//-----------------

void tablou::modificaTablou()

{

date[0]=date[0]+11;

// mareste primul element cu 11

}

//-----------------

void tablou::afisare()

{

for(int i=0;i<dim;i++) cout<<date[i]<<’ ’;

cout<<endl;

}

//-----------------

void main()

{

tablou t1(15,0), t2(25,1);

t1.afisare();

t2.afisare();

tablou t3(t2);

t3.modificaTablou();

t3.afisare();

}

Deoarece, în acest exemplu, este creat un constructor de copiere explicit (corect), orice schimbări asupra obiectului t3 nu afectează obiectul t2 şi invers.

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]