Contents:
Introduction
Questions
Object Creation
Virtual Methods and Inheritance
Trait Classes
Values, References, and Constant References
Answers
Object Creation
Virtual Methods and Inheritance
Trait Classes
Values, References, and Constant References
The implementation of POOMA uses many advanced or obscure features of the ANSI/ISO C++ standard. Its interface is less exacting, but programmers must still have a solid understanding of C++ to use it effectively. If you feel comfortable with the questions below, and their answers, you should have little or no difficulty using POOMA. If, on the other hand, you find the questions and their answers difficult, you may wish to look at some of the books in the recommended reading before trying to use this library.
Fred red; Fred func( Fred cyan ){ Fred magenta; magenta = cyan; return magenta; } int main() { Fred green = red; blue = func(green); return 0; }
What does the following program print out?
#include <iostream> #include <iomanip> using namespace std; class A { public : A() { cout << "A new" << endl; } virtual void left() { cout << "A left" << endl; } void right() { cout << "A right" << endl; } }; class B : public A { public : B() { cout << "B new" << endl; } void left() { cout << "B left" << endl; } void right() { cout << "B right" << endl; } }; int main() { A a; a.left(); a.right(); cout << endl; B b; b.left(); b.right(); cout << endl; A * ap = &b; ap->left(); ap->right(); cout << endl; A * ap = (A*)&b; ap->left(); ap->right(); cout << endl; ap->A::left(); ((A*)ap)->left(); ((A*)ap)->right(); return 0; }
What does the following program print out?
class Blue { public : enum { Val = 240; }; }; template<class T> class Green { public : const int Val = 88; }; template<class T> class Red { public : enum { Val = T::Val/2; }; }; int main() { cout << Blue::Val << endl; cout << Green<Blue>::Val << endl; cout << Red<Blue>::Val << endl; cout << Red<Green<Blue>>::Val << endl; cout << Red<Green<Green<Blue>>>::Val << endl; cout << Red<Red<Green<Blue>>>::Val << endl; return 0; }
Which of the calls to value(), reference, and const_reference below produce errors during compilation?
void value(int x) {} void reference(int & x) {} void const_reference(const int & x) {} int main() { int x; const int y = 2; value(1); value(x); value(y); value(x+1); reference(1); reference(x); reference(y); reference(x+1); const_reference(1); const_reference(x); const_reference(y); const_reference(x+1); return 0; }
The listing below shows where constructor calls and assignments occur:
Fred red; // default constructor Fred func( Fred cyan // copy constructor // (pass by value) ){ Fred magenta; // default constructor magenta = cyan; // assignment operator return magenta; // copy constructor // (magenta is copied into // a nameless temporary to // be returned) } int main() { Fred green = red; // copy constructor blue = func(green); // copy constructor twice // ('green' is copied into // 'cyan' during call, and // temporary return value // is copied into 'blue' on // exit) return 0; }
The program prints the following:
A new // A::A() A left // A::left() A right // A::right() A new // B::B() invokes A::A() B new // body of B::B() B left // B::left() B right // B::right() B left // left() is virtual A right // right() is not virtual B left // cast on right irrelevant A right // right() is not virtual A left // exact method named B left // cast on left irrelevant A right // right() is not virtual
The key here is that Green always defines its own Val, while Red defines its Val in terms of its argument class's Val. The answer is therefore:
int main() { cout << Blue::Val << endl; // 240 cout << Green<Blue>::Val << endl; // 88 cout << Red<Blue>::Val << endl; // 120 cout << Red<Green<Blue>>::Val << endl; // 44 cout << Red<Green<Green<Blue>>>::Val << endl; // 44 cout << Red<Red<Green<Blue>>>::Val << endl; // 22 return 0; }
The only outright errors occur when a constant value (such as a literal or the result of an arithmetic expression) is passed where a non-constant reference parameter is expected. There is also a warning when x is used before being assigned a value:
int main() { int x; const int y = 2; value(1); value(x); // Warning, value used before set. value(y); value(x+1); reference(1); // Error. Non-const reference to const. reference(x); reference(y); // Error. Non-const reference to const. reference(x+1); // Error. Non-const reference to const. const_reference(1); const_reference(x); const_reference(y); const_reference(x+1); return 0; }
[Prev] | [Home] | [Next] |