Programarea in limbajul C++ Supraîncărcarea operatorilor

1 Scopul lucrării:
Studierea necesităţii supraîncărcării operatorilor;
Studierea sintaxei de definire a operatorilor;
Studierea tipurilor de operatori;
Studierea formelor de supraîncărcare;

Sarcina lucrari:
Sa se creeze clasa stack – vector, utilizînd memoria dinamică. Să se defineasca urmatorii operatori ca  metode ale clasei: ” + ”- de adunare a doi vectori, ” - ” – de scadere a doi vectori, ” * ” – de imultirea a doi vectori, ” () ” – de returnare a unui vector nou care conşine ultimele N elemente ale vectorului, ” + ” – cu un numar. Să se definească operatorii de comparare: ”==”, ”!=”, ”<”, ”>” ca funcţii prietene.
Să se definească operatorii ”<<” şi ”>>” pentru ieşiri/intrări de obiecte. Clasa trebuie să fie absolut funcţională, adică să conţină toţi constructorii necesari şi destructorul. 



2 Indicatii teoretice
       Avantajul utilizării operatorilor (reducerea codului) în acelaşi timp complică înţelegerea codului, deoarece nu este posibil întotdeauna sau este complicat să se urmărească dacă se utilizează un operator predefinit sau supraîncărcat. Însă supraîncărcarea operatorilor este necesară. Sunt probleme care se soluţionează numai prin supraîncărcarea operatorilor,cum ar fi operatorul de atribuire.
Functiile prietene sunt functii care nu sunt metode ale unei clase, dar care au totusi acces la membrii   privati ai acesteia. Orice functie poate fi prietena a unei clase, indiferent de natura acesteia.

2.1 Supraîncărcarea
Prin supraîncărcarea unui operator, acesta este utilizat în contexte diferite, avînd aceeaşi semnificaţie sau o semnificaţie diferită. Astfel operatorul + este supraîncărcat pentru adunarea întregilor şi a realilor; operatorul << este supraîncărcat cu semnificaţia de deplasare la stînga, dacă termenii sunt întregi  sau inserare în flux, dacă un termen este un flux de date, iar celălalt un obiect.
    Programatorul poate asocia noi semnificaţii operatorilor existenţi prin supraîncărcarea operatorilor. Vom evita folosirea termenului redefinire, căruia îi vom da o semnificaţie diferită, în contextul moştenirii.
    Anumiţi operatori pot fi utilizaţi cu orice tip de termeni (sunt deja supraîncărcaţi global de către compilator). Aceştia sunt: new, delete, sizeof, ::, =, &, ->*, .*, ., ->.
    Pot fi supraîncărcaţi următorii operatori:
+  -  *  /  %  ^  &  | ~  !  =  <  >
+=  -=  *=  /=  %=  ^=  &=  |=  >>=  <<=  ==  !=  <=  >=
&&  ||  ++  --  ->*  ,  ->  <<  >>  []  ()
new  new[]  delete  delete[]
    Nu pot fi supraîncărcaţi operatorii: ::, ., .*, ?:, sizeof.

2.2 Crearea si distrugerea obiectelor
    Sa consideram urmatorul program C++:

             void main()
                    {   Point p; }
    In momentul definirii variabilei p, va fi alocat automat spatiul de memorie necesar, acesta fiind eliberat la terminarea programului. In exemplul de mai sus, variabila p este de tip static. In continuare vom modifica acest program pentru a folosi o variabila dinamica (pointer).

void main()
{
Point *p;
p = new Point;
p->x = 5;
p->y = 10;
printf("Aria = %d\n", p->Aria());
delete p;
        }

Ati observat utilizarea unor operatori pe care nu ii cunoasteti din limbajul C: new si delete. C++ introduce o metoda noua pentru gestiunea dinamica a memoriei, similara celei utilizate in C (malloc() si free()), dar superioara si special construita pentru programarea orientata pe obiecte. Operatorul new este folosit pentru alocarea memoriei, iar sintaxa acestuia este:

variabila = new tip;
variabila = new tip(valoare_initiala);
variabila = new tip[n];

Este usor de intuit ca prima varianta aloca spatiu pentru variabila dar nu o initializeaza, a doua varianta ii aloca spatiu si o initializeaza cu valoarea specificata, iar a treia aloca un tablou de dimensiune n. Acest operator furnizeaza ca rezultat un pointer continand adresa zonei de memorie alocate, in caz de succes, sau un pointer cu valoarea NULL (practic 0) atunci cand alocarea nu a reusit.
Eliminarea unei variabile dinamice si eliberarea zonei de memorie aferente se realizeaza cu ajutorul operatorului delete. Sintaxa acestuia este:
delete variabila;

Desi acesti doi operatori ofera metode flexibile de gestionare a obiectelor, exista situatii in care aceasta nu rezolva toate problemele (de exemplu obiectele care necesita alocarea unor variabile dinamice in momentul crearii lor). De aceea pentru crearea si distrugerea obiectelor in C++ se folosesc niste functii membre speciale, numite constructori si destructori.
Constructorul este apelat automat la instantierea unei clase, fie ea statica sau dinamica.
Destructorul este apelat automat la eliminarea unui obiect, la incheierea timpului de viata in cazul static, sau la apelul unuidelete in cazul dinamic.
Din punct de vedere cronologic, constructorul este apelat dupa alocarea memoriei necesare, deci in faza finala a crearii obiectului, iar destructorul inaintea eliberarii memoriei aferente, deci in faza initiala a distrugerii sale.
Constructorii si destructorii se declara si se definesc similar cu celelalte functii membre, dar prezinta o serie de caracteristici specifice:
numele lor coincide cu numele clasei careia ii apartin; destructorii se disting de constructori prin faptul ca numele lor este precedat de caracterul ~
a)  nu pot returna nici un rezultat
b)  nu se pot utiliza pointeri catre constructori sau destructori
c)  constructorii pot avea parametri, destructorii insa nu.
Un constructor fara parametri poarta denumirea de constructor implicit.
De remarcat este faptul ca in cazul in care o clasa nu dispune de constructori sau destructori, compilatorul de C++ genereaza automat un constructor respectiv destructor implicit.
Sa completam in continuare clasa Point cu un constructor si un destructor:
Point::Point()
// constructor implicit
{
x = 0;
y = 0;
}

Point::Point(unsigned X, unsigned Y)
{
x = X;
y = Y;
}

Point::~Point()
{
}
Ati remarcat cu aceasta ocazie modul de marcare a comentariilor in C++: tot ce se afla dupa caracterul // este considerat comentariu.
De notat este faptul ca definitii de forma

Point p;
sau
Point *p = new Point();

duc la apelarea constructorului implicit.
O intrebare care poate apare este motivul pentru care am realizat functiile GetX(), GetY(), SetX(), SetY(), cand puteam utiliza direct variabilele membru x si y. Deoarece una din regulile programarii C++, adoptata in general de catre specialisti, este de a proteja variabilele membru (veti afla in capitolul urmator cum), acestea neputand fi accesate decat prin intermediul unor functii, care au rolul de metode de prelucrare a datelor incapsulate in interiorul clasei.

3 Realizarea sarcinii:
Programul dat a fost compus din două fişiere cu numele „File2.h”,(vezi fig.1) şi „File1.cpp”(vezi anexa A) în care se conţine funcţia „pause()” care este folosită pentru vizualizarea programului mai comod şi original, şi definirea unor culori.

Conţinutul fisierului “File2.h”:

Fig. 1
Să incepem sa discutam despre clasa Stack.

class stack{
    int *elem;
    int dim;
public:    stack():elem(NULL),dim(0){};                                   // constructor implicit
               stack(int d):dim(d){elem = new int[d];}                   //constr. explicit
       ~stack(){delete []elem; elem=NULL; dim=0;};                // destructor
               aloc(int d){elem = new int[d]; dim=d;}                    // alocare de memorie
               stack(stack &);                                                             // construct de copiere
               ret(int i){return elem[i];};                             // return elem[ i ]
    friend  istream & operator>>(istream &in, stack &obj);
    friend  ostream & operator<<(ostream &out,stack &obj);
    friend  int operator>( stack &, stack & );
    friend  int operator<( stack &, stack & );
    friend  int operator==(stack &, stack & );
    friend  int operator!=(stack &, stack & );
               stack operator()(int);
               stack operator+(stack);
               stack operator-(stack);
               stack operator+(int);
               stack operator*(stack);  };

Dupa cum se ştie cu ajutorul claselor se realizeaza un vhechi deziderat al programatorilor: unificarea datelor şi a procedurilor. In cazul meu variabilile int *elem, si  int dim, sunt private (default).

Publice sunt doar constructori, destructori, funcţiile (aloc) şi operatorii de supraincarcare a operatiilor de ( adunare, scadere, inmultire etc.) ca funcţii membre sau prietene.

3.1 Constructorul de copiere:

stack :: stack(stack &obj){
this->elem = new int[obj.dim];                      // Alocarea memoriei this->elem, obj.dim - elemente
for (int i = 0; i < obj.dim; i++)
            this->elem[i]=obj.elem[i];  // copierea element cu element;
            this->dim=obj.dim;
   };
3.2 supraincarcarea operatorului  „>>”  (intrare):
Supraîncarcarea acestui operator a fost declarata ca funcţie prietenă.
Cuvîntul neînţeles din această funcţie poate fi: blue şi yellow, care ştiu engleza înţeleg că merge vorba despre culori, şi ar avea dreptate. Mai concret în această funcţie cînd execuţia programului va ajunge la cuvintul definit blue - înlocuieşte codul:

SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), 9); unde 9 este codul culori 
albastru.
şi tot ce urmează dupa el va fi de culoarea albastră;

istream & operator>>(istream & in, stack & obj){
for (int i = 0; i < obj.dim; i++) {
blue; cout<<"V1["; yellow;
cout<<i+1; blue; cout<<"]= ";
white;
in>>obj.elem[i];                   }
return in;
}



Exemplu de execuţie acestui cod va fi (vezi fig.2): 
Fig. 2
3.3 supraincarcarea operatorului  „<<”  (ieşire):

ostream &operator<<(ostream & out, stack & obj){
for (int i  = 0; i < obj.dim; i++)
out<<" "<<obj.elem[i]<<" ";
return out;
white;               // culoarea alb, (default) a programului dat
}
     Exemplu de execuţie acestui cod va fi (vezi fig.3):

Fig. 3
3.4 supraincarcarea operatorului  „+ ” (adunare a doi vectori):

 Conditia de baza pentu efectuarea acestei operaţi este ca trebuie să aibă acelaşi numar de elemente, în cazul meu trebuie sa fie adevarata condiţia: if (dim==v.dim) dacă va fi adevărată se va efectua adunarea,
Daca nu va fi adevărată se va afişa un mesaj de eroare:
else {del; blue; cout<<"Eroarea nu se poate de efectuat operatia de adunare! (dim1!=dim2)";}
Exemplu de execuţia cazului cînd nu coincide dimensiunile vectorilor: (da, culoarea nu e cea mai potrivita )

Funcţia exit(1);  - ieşire forţată din program
del;  - curătă ecranul,

stack stack ::operator +(stack v){
if (dim==v.dim) {                                               // verivicarea daca au acelaşi număr de elemente
stack v1;
v1.aloc(v.dim);                            // alocarea memoriei pentru vectorul v1 (apel la funcţia aloc();)
for (int i = 0; i < v.dim; i++)
v1.elem[i]=elem[i]+v.ret(i);
return v1;                   }
else {del; blue; cout<<"Eroare nu se poate de efectuat operatia de adunare !(dim1!=dim2)"; getch(); exit(1);}
}

3.5 supraincarcarea operatorului  „ –“  (scăderea  a  doi  vectori):
  Supraîncărcarea acestui operator este analogic ca şi operatorului de adunare şi înmulţire, toate sunt declarate ca funcţii membre a clasei.

stack stack ::operator -(stack v){
if (dim==v.dim) {
stack v1;
v1.aloc(v.dim);
for (int i = 0; i < v.dim; i++)
v1.elem[i]=elem[i]-v.ret(i);
return v1;
}
else {del; blue; cout<<"Eroare nu se poate de efectuat operatia de scadere !(dim1!=dim2)"; getch(); exit(1);}
};

3.6 supraincarcarea operatorului  „  * “  (Înmulţirea  a  doi  vectori):

stack stack ::operator *(stack v){
if (dim==v.dim) {
stack v1;
v1.aloc(v.dim);
for (int i = 0; i < v.dim; i++)
v1.elem[i]=elem[i]*v.ret(i);
return v1; }
else {del; cout<<"Eroare nu coincid dimensiuniile vectorilor !"; getch();  };
 };
3.7 supraincarcarea operatorului  „  + “  (vectorului  v1  +   un  N -dat):
      Datorită supraincarcari acestui operator şi anume pentru a putea aduna un vector cu un numar dat.
       Daca nu va fi făcut această supraîncarcare scierea data va fi eronată:
v=v1+2;
unde “v”- este un vector şi “v1”- un vector creat (cel putin 1 element);

      stack stack ::operator +(int n){
     if (dim>0) // daca vor exista elemente in vector, cel putin 1 atunci
       {stack v(dim);        // se crează un vector v (se apeleaza automat constructorul explicit,                
   //unde se aloca memorie necesara)
      for (int i = 0; i < this->dim; i++)
      v.elem[i]=elem[i]+n;
      return v;                            //se returnează vectorul „v” care contine suma vectorului cu „n”
        }
     else {del; blue; cout<<"Eroare vectorul adunat este gol !"; getch(); };

3.8 supraincarcarea  operatorului  „ < “  (operator  de  comparare):
      Supraîncarcarea operatorilor de comparare sunt declarate ca funcţii prietene.

int operator<(stack &v1, stack &v2){
int k;
if (v1.dim<v2.dim)  k=v1.dim;
else k=v2.dim;
for (int i = 0; i < k; i++)
    if (v1.elem[i]>v2.elem[i]) return 0;
    else if (v1.elem[i]<v2.elem[i]) return 1;
if (v1.dim<v2.dim) return 1;
else return 0;  };

3.9 supraincarcarea  operatorului  „  > “  (operator  de  comparare):

int operator>(stack &v1, stack &v2){
int k;
if (v1.dim>v2.dim)  k=v1.dim;
else k=v2.dim;
for (int i = 0; i < k; i++)
    if (v1.elem[i]<v2.elem[i])  return 0;
    else if (v1.elem[i]>v2.elem[i])  return 1;
if (v1.dim>v2.dim)   return 1;
else return 0;
    };


3.10 supraincarcarea  operatorului  „  == “  (operator  de  comparare):

            int operator==(stack & v1, stack &v2){
if (v1.dim!=v2.dim) return 0;
for (int i = 0; i < v1.dim; i++)
if (v1.elem[i]==v2.elem[i]) return 1;
return 0;
};

3.11 supraincarcarea  operatorului  „  != “  (operator  de  comparare):

int operator!=(stack &v1, stack &v2){
if (v1.dim!=v2.dim) return 1;
else if (v1.dim==v2.dim)
for (int  i = 0; i < v1.dim; i++)
 if (v1.elem[i]!=v2.elem[i]) return 1;
 return 0;
};

3.12 supraincarcarea  operatorului  „  ( ) “  (paranteze  rotunde):
Scopul supraîncarcari acestui operator constă în aceia ca sa pot să returnez un vector care este alcătuit din  ultimele N (N – numar dat).
       De exemplu (N=2) vectorul A conţine 5 elemente [2 6 4 -3 1] , se cere să se constuiască vectorul B care va conţine ultimele N(N=2) de aici rezulta că B va conţine [-3 1];
Exemplu cum va rezolva programul această problema:
Fig. 4
 stack stack ::operator ()(int n){
if (n<=this->dim) {        //daca vectorul „venit” contine cel mult „n”  elemente atunci
stack v;                           // se crează un vector suplimentar „v” în care se vor scrii ultimele „n” elemente
int k=0;                          // creez o variabilă de tip intreg, si îi atribui „0”
v.aloc(n);                        // aloc memorie pentru vectorul suplimentar „v”
for (int i = 0; i<=this->dim; i++)   //pornesc un ciclu de la 0 pînă la (cîte elemente are vectorul „venit”)
if (i>=(this->dim-n)) {   // daca „i” va ajunge în intervalul (dim-n) atunci se înscrie acest element de pe
v.elem[k]=this->ret(i);    // pozitia „i” în vectorul „v” suplimentar pe poziţia „k” unde „k” de prima dată este  0,
k++; }                            // după aceasta se incrementează k cu 1;
return v;                         // se returnează vectorul suplimentar „v”
}                                     //daca vectorul „venit” conţine mai puţine elemente ca „n” introdus atunci se
              //afişează mesajul ca am introdus un N mai mare decit numarul de elemente ale vectorului.
else {del; blue; cout<<"Eroare N este mai mare da dimensiunea vectorului !"; getch(); }};

 3.13 funcţia operaţiilor matematice (operatia_M();)
            Funcţia operatia_M() este de tip void, este sun submeniu, din care se poate de ales comanda dorită.
       Datorită acestei functi sa micşorat volumul funcţiei main()
    Cum arată submeniul (vezi Fig.)

Fig. 5
Codul sursă fucţiei operatia_M();
void operatia_M(){
char com;
sus: del;
white; cout<<"1 "; yellow; cout<<"-Suma: V1 + V2"<<endl;
white; cout<<"2 "; yellow;cout<<"-Scaderea: V1 - V2"<<endl;
white; cout<<"3 "; yellow; cout<<"-Produsul: V1 * V2"<<endl;
white; cout<<"4 "; yellow; cout<<"-V1 + N (N - Numar dat)"<<endl;
white; cout<<"5 "; yellow; cout<<"-Compararea V1 si V2"<<endl;
blue; cout<<"Backspace "; white; cout<<"-Inapoi"<<endl;
com=getch();
switch (com) {
  case '1':{           del; cyan;                                                       // del; - curaţă ecranul, cyan; - culoare;
                                       cout<<"Suma: V1 + V2"<<endl;
                                       stack vs;                                              // Vector Suma
                                       vs=v1+v2;
                                       yellow; cout<<"["<<v1<<"]";
                                       white;  cout<<" + ";
                                       cyan;   cout<<"["<<v2<<"]";
                                       yellow;  cout<<" = ";
                                       white; cout<<"["<<vs<<"]";
                                                                                                   break;};
  case '2':{    del; cyan;
                                       cout<<"Scaderea: V1 - V2"<<endl;
                                       stack vsc;                                            //Vector SCcadere
                                       vsc=v1-v2;
                                       yellow; cout<<"["<<v1<<"]";
                                       white;  cout<<" - ";
                                       cyan;   cout<<"["<<v2<<"]";
                                       yellow;  cout<<" = ";
                                       white; cout<<"["<<vsc<<"]";
                                                                                             break;};
  case '3':{    del; cyan;
                                       cout<<"Produsul: V1 * V2"<<endl;
                                       stack vp;                                             //Vector Produs
                                       vp=v1*v2;
                                       yellow; cout<<"["<<v1<<"]";
                                       white;  cout<<" * ";
                                       cyan;   cout<<"["<<v2<<"]";
                                       yellow;  cout<<" = ";
                                       white; cout<<"["<<vp<<"]";
                                                                                           break;};
  case '4':{           del; cyan;
                                       int n;
                                       cout<<"N= ";  cin>>n;
                                       stack vn;                                             //Vector Numar
                                       vn=v1+n;
                                       yellow; cout<<"["<<v1<<"]";
                                       white;  cout<<" + ";
                                       cyan;   cout<<n;
                                       yellow;  cout<<" = ";
                                       white; cout<<"["<<vn<<"]";
                                                                                        break;};


  case '5':{           del; cyan;
                                       if (v1>v2) {
                        yellow; cout<<"["<<v1<<"]";
                        white; cout<<" > ";
                        yellow; cout<<"["<<v2<<"]";            }
                                       else if (v1<v2) {
                        yellow; cout<<"["<<v1<<"]";
                        white; cout<<" < ";
                        yellow; cout<<"["<<v2<<"]";
                                                    }
                                       else  {
                        yellow; cout<<"["<<v1<<"]";
                        white; cout<<" = ";
                        yellow; cout<<"["<<v2<<"]";
                                                    }
                break;};
  case 8 :{goto stop;};    
// daca se testeaza butonul Backspace atunci iese din fincţia operatia_M();
  default :goto sus;  }
getch(); goto sus;
stop:};

3.14 Funcţia MAIN()

     Îm funcţia principală main() se introduc vectori v1 şi v2, se apeleaza la funcţiile necesare cum ar fi     funcţia de returnare a unui vector nou cu ultimele N elemente ale vectorului v1, ea se apelează tastînd tasta   cu numarul 4, (vezi Fig. 6);
Fig. 6
Codul sursă funcţiei de returnare a unui vector nou cu ultimele N elemente


Introducerea vectorului v1 cît şi a v2 sunt la fel (vezi Fig. 7)

Fig. 7

Apelu la funcţia operatia_M() se efectuiază apăsînd tasta cu numarul 3, vezi codul sursă apelului la funcţia data (Fig. 8)

Fig. 8
Ieşirea din program se efectuiază tastînd tasta Esc (vezi Fig. 9)

Fig. 9


Concluzi:
    In urma efectuarii lucrarii date am determinat ca mediul de prgramare C++   este cu mult flexibil ca C, care ne permite sa manipulam cu informatia intr-un mod rapid si eficient fara a induce erori grosolane, si am aflat ca utilizarea claselor este cu mult mai comod si mai rapid in eleborarea unui program.
Am înţeles importanta supraîncarcari operatorilor de adunare, scadere, înmulţire şi anume pentru a permite utilizarea acestora in efectuarea operatiilor cu careva date create de utilizator, în cazul meu a fost vectori, adunarea unor vectori de exemplu (vectorul1+vectorul2) fară supraîncarcarea operatorului de adunare este inmposibilă, şi altor operatori la fel.
Este foarte comod citirea si afişarea unui vector datorita supraîncărcări operatorilor de intrare/ieşire.


Bibliografie
1 TOTUL DESPRE C SI C++ (MANUALUL FUNDAMENTAL DE PROGRAMARE IN C SI C++)[RO][Kris Jamsa][Lars Kland]  
2 PROGRAMARE IN C_C++ CULEGERE DE PROBLEME Valiriu Iorga
3 Initiere in C++, Programarea orientata pe obiecte (Editie Prevazuta) Cluj-Napoca 1993




Anexa A
Fişierul „File1.cpp”
#include <conio.h>
#include <iostream.h>
#include <windows.h>
#include "File2.h"
class stack{
    int *elem;
    int dim;
public:    stack():elem(NULL),dim(0){};                                  // canstructor implicit
               stack(int d):dim(d){elem = new int[d];}     //c. explicit
       ~stack(){delete []elem; elem=NULL; dim=0;};   // destructor
               aloc(int d){elem = new int[d]; dim=d;}       // alocare
               stack(stack &);                              // construct de copiere
               ret(int i){return elem[i];};                 // return
    friend  istream & operator>>(istream &in, stack &obj);
    friend  ostream & operator<<(ostream &out,stack &obj);
    friend  int operator>( stack &, stack & );
    friend  int operator<( stack &, stack & );
    friend  int operator==(stack &, stack & );
    friend  int operator!=(stack &, stack & );
               stack operator()(int);
               stack operator+(stack);
               stack operator-(stack);
               stack operator+(int);
               stack operator*(stack);};
stack v1,v2;                   
//**************************OPERATOR () {returnara a n elem}
stack stack ::operator ()(int n){
if (n<=this->dim) {
stack v;
int k=0;
v.aloc(n);
for (int i = 0; i<=this->dim; i++)
if (i>=(this->dim-n)) {
v.elem[k]=this->ret(i);
k++; }
return v;  }

else {del; blue; cout<<"Eroare N este mai mare da dimensiunea vectorului !"; getch(); }};
//**********************************OPERATOR DE COMPARARE !=
int operator!=(stack &v1, stack &v2){
if (v1.dim!=v2.dim) return 1;
else if (v1.dim==v2.dim)
for (int  i = 0; i < v1.dim; i++)
 if (v1.elem[i]!=v2.elem[i]) return 1;
 return 0;
};
//************************************OPERATOR DE COMPARARE == EGALITATE
int operator==(stack & v1, stack &v2){
if (v1.dim!=v2.dim) return 0;
for (int i = 0; i < v1.dim; i++)
if (v1.elem[i]==v2.elem[i]) return 1;
return 0;  };
//****************************OPERATOR DE COMPARARE >
int operator>(stack &v1, stack &v2){
int k;
if (v1.dim>v2.dim)  k=v1.dim;
else k=v2.dim;
for (int i = 0; i < k; i++)
    if (v1.elem[i]<v2.elem[i])  return 0;
    else if (v1.elem[i]>v2.elem[i])  return 1;
if (v1.dim>v2.dim)   return 1;
else return 0;
    };
//********************************OPERATOR DE COMPARARE <
int operator<(stack &v1, stack &v2){
int k;
if (v1.dim<v2.dim)  k=v1.dim;
else k=v2.dim;
for (int i = 0; i < k; i++)
    if (v1.elem[i]>v2.elem[i]) return 0;
    else if (v1.elem[i]<v2.elem[i]) return 1;
if (v1.dim<v2.dim) return 1;
else return 0;
};
//*********************************************OPERATOR +
stack stack ::operator +(stack v){
if (dim==v.dim) {
stack v1;
v1.aloc(v.dim);
for (int i = 0; i < v.dim; i++)
v1.elem[i]=elem[i]+v.ret(i);
return v1;                   }
else {del; blue; cout<<"Eroare nu se poate de efectuat operatia de adunare !(dim1!=dim2)"; getch(); exit(1);}
}
//*********************************************OPERATOR -
stack stack ::operator -(stack v){
if (dim==v.dim) {
stack v1;
v1.aloc(v.dim);
for (int i = 0; i < v.dim; i++)
v1.elem[i]=elem[i]-v.ret(i);
return v1;
}
else {del; blue; cout<<"Eroare nu se poate de efectuat operatia de scadere !(dim1!=dim2)"; getch(); exit(1);}
};
//*******************************ADUNAREA CU UN NUMAR
stack stack ::operator +(int n){
if (dim>0) // daca vor exista elemente in vector cel putin 1 atunci
{stack v(dim);
for (int i = 0; i < this->dim; i++)
v.elem[i]=elem[i]+n;
return v;
}
else {del; blue; cout<<"Eroare vectorul adunat este gol !"; getch(); };
};
//*******************************************IMULTIREA V1*V2
stack stack ::operator *(stack v){
if (dim==v.dim) {
stack v1;
v1.aloc(v.dim);
for (int i = 0; i < v.dim; i++)
v1.elem[i]=elem[i]*v.ret(i);
return v1; }
else {del; cout<<"Eroare nu coincid dimensiuniile vectorilor !"; getch();  };
 };
//********************************************CONSTR. DE COPIERE
stack :: stack(stack &obj){
this->elem = new int[obj.dim];
for (int i = 0; i < obj.dim; i++)
    this->elem[i]=obj.elem[i];
    this->dim=obj.dim;
};
//*************************************************CIN, >>
istream & operator>>(istream & in, stack & obj){
for (int i = 0; i < obj.dim; i++) {
blue; cout<<"V1["; yellow; cout<<i+1; blue; cout<<"]= ";
white;
in>>obj.elem[i];                   }
return in;
}
//****************************************COUT <<
ostream &operator<<(ostream & out, stack & obj){
for (int i  = 0; i < obj.dim; i++)
out<<" "<<obj.elem[i]<<" ";
return out;
white;
}
//**********************************OPERATI MATEMATICE
void operatia_M(){
char com;
sus: del;
white; cout<<"1 "; yellow; cout<<"-Suma: V1 + V2"<<endl;
white; cout<<"2 "; yellow;cout<<"-Scaderea: V1 - V2"<<endl;
white; cout<<"3 "; yellow; cout<<"-Produsul: V1 * V2"<<endl;
white; cout<<"4 "; yellow; cout<<"-V1 + N (N - Numar dat)"<<endl;
white; cout<<"5 "; yellow; cout<<"-Compararea V1 si V2"<<endl;
blue; cout<<"Backspace "; white; cout<<"-Inapoi"<<endl;
com=getch();
switch (com) {
  case '1':{           del; cyan;
                                       cout<<"Suma: V1 + V2"<<endl;
                                       stack vs;  // Vector Suma
                                       vs=v1+v2;
                                       yellow; cout<<"["<<v1<<"]";
                                       white;  cout<<" + ";
                                       cyan;   cout<<"["<<v2<<"]";
                                       yellow;  cout<<" = ";
                                       white; cout<<"["<<vs<<"]";
                                                                                                   break;};
  case '2':{    del; cyan;
                                       cout<<"Scaderea: V1 - V2"<<endl;
                                       stack vsc;    //Vector SCcadere
                                       vsc=v1-v2;
                                       yellow; cout<<"["<<v1<<"]";
                                       white;  cout<<" - ";
                                       cyan;   cout<<"["<<v2<<"]";
                                       yellow;  cout<<" = ";
                                       white; cout<<"["<<vsc<<"]";
                                                                                                  break;};
  case '3':{    del; cyan;
                                       cout<<"Produsul: V1 * V2"<<endl;
                                       stack vp; //Vector Produs
                                       vp=v1*v2;
                                       yellow; cout<<"["<<v1<<"]";
                                       white;  cout<<" * ";
                                       cyan;   cout<<"["<<v2<<"]";
                                       yellow;  cout<<" = ";
                                       white; cout<<"["<<vp<<"]";
                                                                                                    break;};
  case '4':{           del; cyan;
                                       int n;
                                       cout<<"N= ";  cin>>n;
                                       stack vn; //Vector Numar
                                       vn=v1+n;
                                       yellow; cout<<"["<<v1<<"]";
                                       white;  cout<<" + ";
                                       cyan;   cout<<n;
                                       yellow;  cout<<" = ";
                                       white; cout<<"["<<vn<<"]";
                                                                                        break;};
  case '5':{           del; cyan;
                                       if (v1>v2) {
                   yellow; cout<<"["<<v1<<"]";
                   white; cout<<" > ";
                   yellow; cout<<"["<<v2<<"]";            }
                                       else if (v1<v2) {
                   yellow; cout<<"["<<v1<<"]";
                   white; cout<<" < ";
                   yellow; cout<<"["<<v2<<"]";
                                                    }
                                       else  {
                   yellow; cout<<"["<<v1<<"]";
                   white; cout<<" = ";
                   yellow; cout<<"["<<v2<<"]";
                                                    }
                                                               break;};
  case 8 :{goto stop;};
  default :goto sus;
}
getch(); goto sus;
stop:};

//******************MAIN-ul
void main(){
stack s1;
char com;
sus:del;
white;
yellow;    cout<<"1 "; white; cout<<"- Introdu vectorul V1"<<endl;
yellow; cout<<"2 "; white; cout<<"- Introdu vectorul V2"<<endl;
yellow; cout<<"3 "; white; cout<<"- Operati matematice asupra V1 si V2"<<endl;
yellow; cout<<"4 "; white; cout<<"- Returneaza un Vect. nou cu ultimile N elemente"<<endl;
yellow; cout<<"Esc "; white; cout<<"- Iesire din program"<<endl;
 com=getch();
switch (com) {
               case '1':{         int nv1;
                                                   white;  del;
                              cout<<"Numarul de elemente= ";
                                                   cin>>nv1;
                                                   v1.aloc(nv1);
                                                   cin>>v1;
                                                   pause();                                   break;};
               case '2':{         int nv2;
                                                   white;   del;
                              cout<<"Numarul de elemente= ";
                                                   cin>>nv2;
                                                   v2.aloc(nv2);
                                                   cin>>v2;
                                                   pause();                                   break;};
               case '3':{         operatia_M();              break;};
               case '4':{         del;
                                                   int n;
                                                   blue;
cout<<"Atentie V1 trebuie sa contina cel putin un element"<<endl;
                 cyan;cout<<"Introdu N= "; cin>>n;
                                                   stack vnew(n);
                                                   vnew=v1(n);
                                                   white;
cout<<"Ultemul(-ele) "; cyan; cout<<n; white; cout<<" element(-e) din V1= ";
                                                   yellow; cout<<"["<<v1<<"]";
                                              white;cout<<" este: ";
                       yellow; cout<<"["<<vnew<<"]";
                                                                                                    getch();
                                                                                                                         break;};
               case 27:{pause(); exit(1);}
default: goto sus;
}
goto sus;
getch();} 





Fişierul „File2.h”
# define   white SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), 11)  //alb
# define   yellow SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), 10) //galben
# define   blue SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), 9)    //albastru
# define   cyan SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), 8)    //cyan
# define  del  clrscr();         //curata ecranul
//*************MENU PAUZA
void pause(){
yellow;
cout<<endl<<endl<<"Apasati orice tasta...";
getch();
white;
};

Niciun comentariu: