int returnByValue()
{
return 5;
}
int& returnByReference()
{
static int x{ 5 };
return x;
}
int main()
{
int value{ returnByReference() };
int &ref{ returnByValue() };
const int &cref{ returnByValue() }; return 0; }
-static ensures x isn’t destroyed when the function ends
case A – ok, treated as return by value
case B – compile error since the value is an r-value, and an r-value can’t bind to a non-const reference
case C – ok, the lifetime of the return value is extended to the lifetime of cref
const int& returnByReference()
{
return 5;
}
int main()
{
const int &ref { returnByReference() };
}runtime error
const int returnByValue()
{
return 5;
}
int main()
{
const int &ref { returnByValue() };
}ok, we’re extending the lifetime of the copy passed back to main
string get_name()
{
string s="magic";
return s;
}
int main()
{
string p=get_name();
std::cout<<p></p>ok
#include
using namespace std;
string get_name()
{
string s="magic";
return s;
}
int main()
{
string& p=get_name();
std::cout<<p></p>//nu compileaza //nu ai voie sa faci bind unei referinte de o valoare temporara
#include
using namespace std;
const string& get_name()
{
string s="magic";
return s;
}
int main()
{
string& p=get_name();
std::cout<<p></p>nu compileaza, s-a scapat ilegal de const
#include
using namespace std;
string get_name()
{
string s="magic";
return s;
}
int main()
{
const string& p=get_name();
std::cout<<p></p>/functioneaza, iar valoarea temporara va fi distrusa atunci cand va iesi referinta din scop
#include
using namespace std;
const string& get_name()
{
string s="magic";
return s;
}
int main()
{
const string& p=get_name();
std::coutruntime error, se mosteneste durata de viata a valorii trimise prin const reference si era o variabila locala deci a murit
#include
using namespace std;
string o= "opapa";
const string& get_name()
{
string s="magic";
return o;
}
int main()
{
const string& p=get_name();
std::cout<opapa
Ce e aia lifetime extension? cand functioneaza si cand nu functioneaza?
Functioneaza atunci cand un local const T& sau T&& este initializat din reziltatul unei expresii care returneaza:
-un temporar T
-T subobiectul unui temporar(un struct care contine T)
In cazul acesta, obiectul T este distrus atucni cand referinta iese din scop.
Cand nu merge lifetime extension?
-cand facem assignment la T& nu const T& - eroare de compilare
-cand se face non-polimorfic type conversion. type-conversion e permisa atunci cand faci assignment la T& dintr-un temporar U , unde U este copil al lui T
Compileaza sau nu? Daca da de ce, daca nu de ce?
#include
using namespace std;
struct Person {
struct Name {
std::string first_name;
std::string last_name;
} name;
};
Person birth;
int main()
{
const std::string &first_name = birth.name.first_name;
}Merge, si birth este distrus dupa ultima acolada.
Spuneţi de câte ori se execută fiecare constructor în programul de mai jos şi în ce ordine.
#include
class cls1
{
protected:
int x;
public:
cls1()
{
x=13;
}
};
class cls2: public cls1
{
int y;
public:
cls2()
{
y=15;
}
int f(cls2 ob)
{
return (ob.x+ob.y);
}
};
int main()
{
cls2 ob;
cout<eroare: - nu exista
- lipseste namespace std si avem cout
- daca nu ar lipsi s-ar afisa 28
- se apeleaza cls1(), cls2(), cls1(ob), cls2(ob)
Spuneţi dacă programul de mai jos este corect. În caz afirmativ, spuneţi ce afişează, altfel, spuneţi de ce nu este corect.
#include
class cls1
{
int x;
public:
cls1()
{
x=13;
}
int g()
{
static int i;
i++;
return (i+x);
}
};
class cls2
{
int x;
public:
cls2()
{
x=27;
}
cls1& f()
{
static cls1 ob;
return ob;
}
};
int main()
{
cls2 ob;
std::cout<se afiseaza 14
static in funtie face sa nu se distruga obiectul la iesirea din functie
#include
class cls1
{
protected:
int x;
public:
cls1(int i=10)
{
x=i;
}
int get_x()
{
return x;
}
};
class cls2: cls1
{
public:
cls2(int i):cls1(i) {}
};
int main()
{
cls d(37);
std::cout<-nu exista clasa cls
Ruleaza sau nu? Daca da, de ce, daca nu, de ce? #include
class Money
{
public:
Money() : amount{ 0.0 } {};
Money(double _amount) : amount{ _amount } {};
explicit operator double() const { return amount; } private:
double amount; };void display_balance(const Money balance)
{
std::cout << "The balance is: " << balance << std::endl;
}Nu ruleaza pentru ca explicit la conversion opeartor previne conversia implicita catre tipul catre care se converteste.
Ruleaza sau nu? Daca da, de ce, daca nu, de ce? #include
class Money
{
public:
Money() : amount{ 0.0 } {};
Money(double _amount) : amount{ _amount } {};
double operator double() const { return amount; } private:
double amount; };void display_balance(const Money balance)
{
std::cout << "The balance is: " << balance << std::endl;
}Nu ruleaza pentru ca e ilegal sa pui return type la conversion function.
Ruleaza sau nu? Daca da, de ce, daca nu, de ce? #include
class Money
{
public:
Money() : amount{ 0.0 } {};
Money(double _amount) : amount{ _amount } {};
operator double(double x) const { return amount+x; }
private:
double amount;
};
void display_balance(const Money balance)
{
std::cout << "The balance is: " << balance << std::endl;
}Nu ruleaza pentru ca e ilegal sa pui parametri ca conversion operator.
#include
class cls
{
int x;
public:
cls(int y)
{
x=y;
}
int operator*(cls a,cls b)
{
return (a.x*b.x);
}
};
int main()
{
cls m(100),n(15);
cout<Eroare: operatorul * poate primi 0 sau 1 argument.
Spuneţi de câte ori este moştenită clasa B în clasa M1. Dar în clasa M2 ? Justificaţi.
class B { /* instructiuni */ };
class D1: virtual B { /* instructiuni */ };
class D2: virtual B { /* instructiuni */ };
class D3: B { /* instructiuni */ };
class D4: private B { /* instructiuni */ };
class D5: virtual public B { /* instructiuni */ };
class M1: D1, public D2, D3, private D4, virtual D5
{ /* instructiuni */ };
class M2: D1, D2, virtual D3, virtual D4, virtual D5
{ /* instructiuni */ };Pentru M1: de 3 ori :B() D5() D1() D2() B() D3() B() D4() M1()
Pentru M2: de 3 ori B() B() D3() B() D4() D5() D1() D2() M2()
#include
using namespace std;
class B1
{
public:
int x;
};
class B2
{
int y;
};
class B3
{
public:
int z;
};
class B4
{
public:
int t;
};
class D: private B1, protected B2, public B3, B4
{
int u;
};
int main()
{
D d;
cout<doar pentru z e corect
#include
class cls
{
int vi;
public:
cls(int v=37)
{
vi=v;
}
friend int& f(cls);
};
int& f(cls c)
{
return c.vi;
}
int main()
{
const cls d(15);
f(d)=8;
std::cout<compileaza, dar nu se afiseaza nimic pentru ca returnez adresa unui int
#include
class cls1
{
public:
int x;
cls1(int i=20)
{
x=i;
}
};
class cls2
{
public:
int y;
cls2(int i=30)
{
y=i;
}
operator cls1()
{
cls1 ob;
ob.x=y;
return ob;
}
};
cls1 f(cls1 ob)
{
ob.x++;
return ob;
}
int main()
{
cls1 ob1;
f(ob1);
std::cout<2030
#include
class cls
{
int x;
public:
cls(int i=25)
{
x=i;
}
int f();
};
int cls::f()
{
return x;
}
int main()
{
const cls d(15);
std::cout<passing ‘const cls’ as ‘this’ argument discards qualifiers – ar trebui ca functia sa fie const si atunci s-ar afisa 15
#include
class cls
{
public:
int x;
cls(int i=0)
{
x=i;
}
};
cls f(cls c)
{
c.x++;
return c;
}
int main()
{
cls r(10);
cls s=f(r);
return 0;
}compileaza