Ласло Краус |
ИР2ОО1/СИ2ОО1 Испит 14. 1. 2011. |
|---|
Одговорити концизно (једна или две реченице) и прецизно на следећа питaња:
а) Да ли тип аргумента конструктора неке класе може бити: (1) сама та класа, (2) показивач на ту класу, (3) упућивач (референца) на ту класу?
б) Ако је основна класа изузетака Е, из ње изведена класа Е1, а из Е1 изведена класа Е2, којим редом треба написати catch гране за обраду сва три типа изузетака?
в) Чему служи специјализација шаблона?
Написати на језику C++ следеће класе (класе опремити оним конструкторима, деструктором и оператором за доделу вредности, који су потребни за безбедно коришћење класа; грешке пријављивати изузецима типа једноставних класа које су опремљене писањем текста поруке):
S.
B.
niz+=&stvar; грешка је ако се низ препуни). Може да се дохвати број ствари у низу, и да се приступи ствари са затим редним бројем (niz[ind]; грешка је ако је индекс изван опсега).
it<<vozilo). Возило не може да се копира ни на који начин. Вучна снага представља тежину терета који може да повуче.
L(укТежина|вучнаСнага).
vagon+=&teret). Вучна снага вагона је 0. У излазни ток се пише у облику V(укТежина|терет,…,терет).
voz+=&vozilo; грешка је ако се воз преоптерети, тј. ако укупна тежина свих возила и терета премаши укупну вучну снагу возила у возу). Може да се дохвати број возила у возу, да се провери да ли би се воз преоптеретио прикључивањем задатог возила и да се воз упише у излазни ток (it<<voz; пишу се садржана возила, по једно возило у реду). Воз не може да се копира ни на који начин.
(5 поена) Написати на језику C++ програм који направи воз са једном локомотивом и два вагона са по два терета. Користити фиксне параметре (не треба ништа учитавати с главног улаза).
#include <iostream>
using namespace std;
class Teret {
static int posId;
int id;
double sigma;
public:
explicit Teret(double s=1) { id = ++posId; sigma = s; }
Teret(const Teret& t) { id = ++ posId; sigma = t.sigma; }
virtual ~Teret() {}
Teret& operator= (const Teret& t) { sigma = t.sigma; }
virtual char vrsta() const =0;
virtual Teret* kopija() const =0;
virtual double zapr() const =0;
double tezina() const { return zapr() * sigma; }
friend ostream& operator<< (ostream& it, const Teret& t)
{ return it << t.vrsta() << t.id; }
};
int Teret::posId = 0;
class Sanduk: public Teret {
double a, b, c;
public:
explicit Sanduk(double s=1, double aa=1, double bb=1, double cc=1):
Teret(s), a(aa), b(bb), c(cc) {}
char vrsta() const { return 'S'; }
double zapr() const { return a*b*c; }
Sanduk* kopija() const { return new Sanduk(*this); }
};
class Bure: public Teret {
double r, h;
public:
explicit Bure(double s=1, double rr=1, double hh=1):
Teret(s), r(rr), h(hh) {}
char vrsta() const { return 'B'; }
double zapr() const { return r * r * 3.14159 * h; }
Bure* kopija() const { return new Bure(*this); }
};
class GIndeks {};
inline ostream& operator<< (ostream& it,
const GIndeks&) { return it << "*** Nedozvoljen indeks!"; }
class GPun {};
inline ostream& operator<< (ostream& it, const GPun&)
{ return it << "*** Niz je pun!"; }
template <typename T>
class Niz {
T** niz; int kap, duz;
void kopiraj(const Niz& n);
void brisi();
public:
explicit Niz(int k=10) { niz = new T* [kap = k]; duz = 0; }
Niz(const Niz& n) { kopiraj(n); }
~Niz() { brisi(); }
Niz& operator= (const Niz& n) {
if (this != &n) { brisi(); kopiraj(n); }
return *this;
}
int duzina() const { return duz; }
Niz& operator+= (T* t) {
if (duz == kap) throw GPun();
niz[duz++] = t;
return *this;
}
T& operator[] (int i) {
if (i<0 || i>=duz) throw GIndeks();
return *niz[i];
}
const T& operator[] (int i) const {
if (i<0 || i>=duz) throw GIndeks();
return *niz[i];
}
};
template <typename T>
void Niz<T>::kopiraj(const Niz& n) {
niz = new T* [kap = n.kap];
duz = n.duz;
for (int i=0; i<duz; i++) niz[i] = n.niz[i]->kopija()
}
template <typename T>
void Niz<T>::brisi() {
for (int i=0; i<duz; delete niz[i++]);
delete [] niz;
}
class Vozilo {
double sopTez;
Vozilo(const Vozilo&) {}
void operator= (const Vozilo&) {}
public:
explicit Vozilo(double st){sopTez=st;}
virtual ~Vozilo() {}
virtual double ukTezina() const { return sopTez; }
virtual double vucnaSnaga() const =0;
private:
virtual void pisi(ostream& it)const=0;
friend ostream& operator<< (ostream& it, const Vozilo& v)
{ v.pisi(it); return it; }
};
class Lokomot: public Vozilo {
double vSnaga;
void pisi(ostream& it) const
{ it << "L(" << ukTezina() << '|' << vSnaga << ')'; }
public:
Lokomot(double st, double vs):
Vozilo(st), vSnaga(vs) {}
double vucnaSnaga() const { return vSnaga; }
};
class Vagon: public Vozilo {
Niz<Teret> niz;
void pisi(ostream& it) const;
public:
Vagon(double st, int k): Vozilo(st), niz(k) {}
Vagon& operator+= (Teret* t) { niz += t; return *this; }
double ukTezina() const;
double vucnaSnaga() const {return 0;}
};
void Vagon::pisi(ostream& it) const {
it << "V(" << ukTezina() << "|";
for (int i=0; i<niz.duzina(); i++) {
if (i > 0) it << ',';
it << niz[i];
}
it << ')';
}
double Vagon::ukTezina() const {
double t = Vozilo::ukTezina();
for (int i=0; i<niz.duzina(); i++) t += niz[i].tezina();
return t;
}
class GPreopt {};
inline ostream& operator<< (ostream& it, const GPreopt&)
{ return it << "*** Voz je preopterecen!"; }
class Voz {
Niz<Vozilo> niz;
Voz(const Voz&) {}
void operator= (const Voz&) {}
public:
explicit Voz(int k): niz(k) {}
int duzina() const { return niz.duzina(); }
bool preopt(Vozilo* v) const;
Voz& operator+= (Vozilo* v) {
if (preopt(v)) throw GPreopt();
niz += v;
return *this;
}
friend ostream& operator<< (ostream& it, const Voz& v);
};
bool Voz::preopt(Vozilo* v) const {
double teret = 0, snaga = 0;
for (int i=0; i<niz.duzina(); i++) {
teret += niz[i].ukTezina();
snaga += niz[i].vucnaSnaga();
}
return teret + v->ukTezina() > snaga + v->vucnaSnaga();
}
ostream& operator<< (ostream& it, const Voz& v) {
for (int i=0; i<v.niz.duzina(); i++)
it << v.niz[i] << endl;
return it;
}
int main() {
try {
Voz voz(3);
voz += new Lokomot(200, 3000);
Vagon* vag = new Vagon(100, 5);
*vag += new Sanduk(3, 2, 1, 3);
*vag += new Bure(2, 2, 4);
voz += vag;
vag = new Vagon(150, 10);
*vag += new Sanduk(4, 2, 10, 3);
*vag += new Bure(6, 3, 8);
voz += vag;
cout << voz << endl;
} catch (GPreopt g) {
cout << g << endl;
} catch (GPun g) {
cout << g << endl;
}
return 0;
}
L(200|3000)
V(218.531|S1,B2)
V(1747.17|S3,B4)
(⇒ почетак)
Copyright © 2011, Laslo Kraus
Последња ревизија: 7.2.2011.