zestaw3

Transkrypt

zestaw3
IMIĘ i NAZWISKO: PRZYKŁADOWE ODPOWIEDZI
NR: 0
EGZAMIN „TERMIN DRUGI” (1 WRZEŚNIA 2014) – JĘZYK C++
1. Opisz, co to jest: T const * const
Stały wskaźnik do stałego obiektu (typu T)
2. Jakiego typu jest obiekt mypointer:
using pointer = int*;
using cpointer = const pointer;
cpointer mypointer;
mypointer jest typu int* (patrz slajd 93 z wykładu)
3. Czy poniższy fragment kodu może działać? Uzasadnij:
auto fun( int );
auto zmienna = fun (5);
Nie może, ponieważ w przypadku autodedukcji zwracanego typu, przed wywołaniem funckji
musi nastąpić jej definicja, a nie tylko deklaracja (rzecz dotyczy oczywiście C++14).
4. Proszę napisać deklaracje funkcji fun, która nic nie zwraca, a przyjmuje argument typu int:
a) przez stałą wartość b) przez referencję do stałego obiektu
c) przez referencję do prawej wartości d) przez wskaźnik do stałego obiektu
a) void fun(const int);
b) void fun(const int&);
c) void fun(int&&);
d) void fun(const int*);
5. Opisz krótko co to jest "dekorowanie" (ang. name mangling) i do czego służy.
Sposób, w jaki kompilator zamienia nazwy funkcji i ich argumentów w unikatowe rozróżnialne
nazwy (dzięki czemu w danym zakresie ważności może istnieć więcej niż jedna funkcja o tej
samej nazwie - przeciążanie/przeładowanie), poprzez dodanie przedrostków i przyrostków do
nazwy rdzeniowej.
6. Wpisz w miejsce kropek konieczne flagi dla kompilatora g++ żeby kod mógł skompilować się,
uwzględniając standard C++11: g++ -std=c++11 kod.cc -o program
Ewentualnie inne flagi: -std=c++0x i tak dalej…
7. W jakiej kolejności będą uruchamiane konstruktory:
struct A { };
struct B : virtual A { };
kolejność: A B A C
struct C : B, A { };
int main() { C c; }
8. Zaznacz, które z poniższych typów zmiennych są niepoprawnie zapisane:
a) unsigned long long
b) wchar_t
c) long double
d) unsigned float to jest źle (typy zmiennoprzecinkowe są tylko signed)
9. Jaki jest dokladnie typ zmiennej jak poniżej:
auto zmienna = { 1, 2, 3 };
zmienna jest typu std::initializer_list<int>
1
10. Klasa B dziedziczy z klasy A, na różne sposoby. W jakich polach dostępności znajdują się
odziedziczone składniki, w zależności od sposobu dziedziczenia (lub napisać "niedostępne"):
klasa A (dziedziczenie publiczne) klasa B
private:
protected:
patrz slajd 199 z wykładu
public:
klasa A (dziedziczenie chronione) klasa B
private:
protected:
public:
klasa A (dziedziczenie prywatne) klasa B
private:
protected:
public:
11. Napisz przykład kompletnego silnego typu wyliczeniowego (z kilkoma identyfikatorami)
opartego na typie short.
enum class Przyklad : short { raz, dwa, trzy }; // zamiast class może być struct
12. Zapisz za pomocą typu std::array dwuwymiarową tablicę typu int (z zagnieżdżonym array)
o rozmiarze 2x4 (2 wiersze, 4 kolumny).
array< array< int, 4>, 2 > tablica;
13. Napisz ogólnie jakie cechy mają obiekty, będące tak zwanymi "prawymi wartościami".
Nie mają nazwy, nie mają (nie znamy go) adresu, zwykle są to obiekty tymczasowe. Mogą
uczestniczyć w operacji przenoszenia.
14. Opisz podstawowe typy hierarchii obiektowej (plus jakiś prosty ilustrujący rysunek).
dziedziczenie, zawieranie (rysunke jak na slajdzie 122)
15. Co to jest this (jego typ, gdzie jest przekazywany).
this - stały wskaźnik (jeśli metoda jest stała, to stały wskaźnik do stałego obiektu)
przekazywany niejawnie każdej zwykłej metodzie składowej klasy, aby metoda znała adres
obiektu, na rzecz którego ma działać
16. Zakreśl te stwierdzenia, które są błędne. Klasę można zdefiniować:
a) w przestrzeni globalnej
b) w przestrzeni nazw
wszystkie są poprawne
c) w funkcji
d) w innej klasie
17. Oto kilka deklaracji destruktora. Wskaż te niepoprawne.
a) virtual ~Klasa();
b) ~Klasa( int c = 0 ); // źle, (destruktor nie może mieć żadnego parametru, nawet domyślnego)
c) ~Klasa() = 0; // źle, (gdyż brakuje virtual albo nie może być = 0)
d) double ~Klasa(); // źle, (destruktor "niczego" nie zwraca, zła składnia)
2
18. Dla poniższej klasy napisz operator rzutowania (kompletny, o dowolnym przepisie) na typ int,
będący metodą stałą:
class A { int n;
public:
operator int() const { return n; }
};
19. Dla klasy A zdefiniuj jak należy operator<< tak, żeby obiekty A dało się wysłać do strumienia:
class A { int n;
friend ostream& operator<<( ostream& s, const A& a );
};
ostream& operator<<( ostream& s, const A& a ) {
return s << a.n;
}
20. Jakiego rodzaju (nie chodzi o typ) obiekt zwraca poniższa funkcja:
const string fun() { return "abcde"; }
funkcja zwraca stałą prawą wartość
21. Napisz wewnątrz klasy deklaracje zablokowanego konstrktora kopiującego i domyślnego
konstruktora przenoszącego.
class A { public:
A();
A( const A& ) = delete;
A( A&& ) = default;
};
22. Zapisz wewnątrz operatora= instrukcję przypisania tak, żeby realizowała poprawnie operację
przenoszenia.
class A { string s;
public:
A& operator=( A&& a ) { // ewentualnie sprawdzić czy źródło i cel to nie te same obiekty
s = std::move( a.s );
return *this;
}
};
23. Proszę napisać klasę Foo taką, że obiekt jej typu będzie można utworzyć tylko na stercie.
Trzeba zablokować destruktor, np. poprzez deklarację w części prywatnej lub zapis
~Foo() = delete; dodatkowo w części publicznej jakąś metodę, wykonującą kasowanie zasobu
(zawierającą "delete this;").
24. Mamy klasę A jak poniżej, zdefiniuj i zainicjalizuj polem n wskaźnik na tę składową klasy:
class A { public:
int n;
};
int A::*wsk = &A::n;
3
25. Napisz, dla dowolnej klasy Foo, deklarację (jako metody składowej klasy) operatora
inkrementacji, przedrostkowego i przyrostkowego.
class Foo { public:
const Foo& operator++(); // przedrostkowy
const Foo operator++(int); // przyrostkowy, generalnie można zwrócić bez const
};
26. Proszę zdefiniować operator= kopiujący w klasie Foo:
class Foo { int n; public:
Foo& operator=(const Foo& s) {
if (this != &s) { n = s.n; }
return *this;
}
};
27. Napisz typ będący wskaźnikiem na stałą metodę składową klasy Foo, przyjmującą jako
argument wskaźnik na int i zwracającą referencję do int.
int& (Foo::*)(int*) const;
28. Proszę podać klasyfikację rodzajów pamięci w języku c++ (z dwoma słowami charakterystyki):
Pamięć statyczna, stos, sterta (więcej np. na slajdzie 48 i 187).
29. Zdefiniuj i zainicjalizuj dowolnymi wartościami początkowymi dynamicznie utworzoną
3-elementową tablicę typu int.
int* wsk = new int[3] { 0, 1, 2 };
30. Jak należy napisać deklarację konstruktora 1-argumentowego, żeby zablokować niejawne
konwersje?
Deklarację poprzedzić słowem explicit
31. Który konstruktor będzie wywołany?
class A {
A(initializer_list<int>); // *1*
public:
A(int, int); // *2*
A(initializer_list<double>); // *3*
};
A obiekt{ 0, 1 };
*1* po czym nastąpi zgłoszenie błędu o niedostępności (prywatności) konstruktora
Ponieważ ściśle ujmując to będzie tylko próba, więc uznaję również odpowiedź, że „żaden”.
32. Proszę dla tablicy double tab[10]; napisać pętlę po całym zakresie (pętlę typu range-based
loop) wpisującą w każdą pozycję tablicy kwadrat wielkości.
for (auto& x : tab) x = x*x;
33. Napisz wyrażenie lambda wpisujące w każdą pozycję wektora kwadrat wartości.
vector<double> v;
std::transform( v.begin(), v.end(), v.begin(), [](double d)->double{ return d*d; } );
34. Niech lista to obiekt typu std::list<char>. Proszę napisać instrukcję sortującą według kryterum
"większy niż". lista.sort( greater<char>() );
35. Podczas wielokrotnego dziedziczenia dla klasy Base, w jaki sposób uniknąć problemów
związanych z niejednoznacznością? dziedziczyć wirtualnie (virtual na liście pochodzenia)
4