31: }
32:
33: void myClass::ShowMember()
34: {
35: cout << "itsMember: " << itsMember << endl;
36: }
37:
38: void myCIass:: ShowSecond()
39: {
40: cout << "itsSecond: " << itsSecond << endl;
41: }
42:
43: void myClass::ShowThird()
44: {
45: cout << "itsThird: " << itsThird << endl;
46: }
47: int myClass::itsStatic = 0;
48:
49: int myClass::GetStatic()
50: {
51: return itsStatic;
52: }
53:
54: int main()
55: {
56: void (myClass::*PMF) ();
57:
58: myClass obj1;
59: PMF=myClass::ShowMember;
60: (obj1.*PMF)();
61: PMF=myClass::ShowSecond;
62: (obj1.*PMF)();
63: PMF=myClass::ShowThird;
64: (ob]1 "PMF)();
65: cout << "Static: " << myClass::GetStatic() << endl;
66:
67: myClass obj2;
68: PMF=myClass::ShowMerober;
69: (obj2.*PMF)();
70: PMF=myClass::ShowSecond;
71: (obj2.*PMF)();
72: PMF=myClass::ShowThird;
73: (obj2. *PMF)();
74: cout << "Static: " << myClass::GetStatic() << endl;
75:
76: myClass obj3;
77: PMF=myClass::ShowMember;
78: (obj3. *PMF)();
79: PMF=myClass::ShowSecond;
80: (obj3.*PMF)();
81: PMF=royClass::ShowThird;
82: (obj3.*PMF)();
83: cout << "Static: " << myClass::GetStatic() << endl;
84: return 0;
85: }
День 15
Контрольные вопросы
1. Как объявить класс, являющийся частным проявлением другого класса?
С помощью открытого наследования.
2. Как объявить класс, объекты которого должны использоваться в качестве переменных-членов другого класса?
Необходимо использовать вложение классов.
3. В чем состоят различия между вложением и делегированием?
Под вложением понимают использование объектов одного класса в качестве переменных-членов другого класса. Под делегированием — передачу одним классом другому классу выполнения некоторых специфических функций. В то же время делегирование часто реализуется за счет вложения классов.
4. В чем состоят различия между делегированием и выполнением класса в пределах другого класса?
Под делегированием понимают передачу одним классом другому классу выполнения некоторых специфических функций. Под реализацией в пределах другого класса — наследование выполнения специфических функций от другого класса.
5. Что такое функция-друг?
Это функция, объявленная с целью получения доступа к защищенным и закрытым членам другого класса.
6. Что такое класс-друг?
Зто класс, объявленный таким образом, чтобы все его функции-члены были дружественными по отношению к другому классу.
7. Если класс Dog является другом Boy, то можно ли сказать, что Boy — друг Dog?
Нет, дружественность классов не взаимна.
8. Если класс Dog является другом Boy, а Terrier произведен от Dog, является ли Terrier другом Boy?
Нет, дружественность классов не наследуется.
9. Если класс Dog является другом Boy, а Boy — другом House, можно ли считать Dog другом House?
Нет, дружественность классов не ассоциативна.
10. Где необходимо размешать объявление функции-друга?
В любом месте внутри объявления класса. Не имеет никакого значения, в каком именно разделе будет помешено это объявление — в public:, protected: или private:.
Упражнения
1. Объявите класс Animal (Животное), который содержит переменную-член, являющуюся объектом класса String.
class Animaclass="underline"
{
private:
String itsName;
};
2. Опишите класс BoundedArray, являющийся массивом.
class boundedArray : public Array
{
// ...
}
3. Опишите класс Set, выполняемый в пределах массива BoundedArray.
class Set : private Array
{
// ...
}
4. Измените листинг 15.1 таким образом, чтобы класс String включал перегруженный
оператор вывода (>>).
1: #include <iostream.h>
2: #include <string.h>
3:
4: class String
5: {
6: public:
7: // конструкторы
8: String();
9: String(const char *const):
10: String(const String &);
11: ~String();
12:
13: // перегруженные операторы
14: char & operator[](int offset);
15: char operator[](int offset) const:
16: String operator+(const String&);
17: void operator+=(const String&);
18: String & operator= (const String &);
19: friend ostream& operator<<
20: ( ostream& _theStream,String& theString);
21: friend ist.ream& operator>>
22: ( istream& _theStream,String& theString);
23: // Общие функции доступа
24: int GetLen()const { return itsLen; }
25: const char * GetString() const { return itsString; }
26: // static int ConstructorCount:
27:
28: private:
29: String (int); // закрытый конструктор
30: char * itsString;
31: unsigned short itslen;
32:
33: };
34:
35: ostream& operator<<( ostream& theStream,String& theStnng)
36: {
37: theStream << theString.GetString();
38: return theStream;
39: }
40:
41: istream& operator>>( istream& theStream,String& theString)
42: {
43: theStream >> theString.GetString();
44: return theStream;
45: }
46:
47: int main()
48: {
49: StringtheString("npHBeT, мир.");
50: cout << theString;
51: return 0;
52: }
5. Жучки: что неправильно в этой программе?
1: #include <iostrearm.h>
2:
3: class Animal;
4:
5: void setValue(Animal& , int);
6:
7:
8: class Animal
9: {
10: public:
11: int GetWeight()const { return itsWeight; }
12: int GetAge() const { return itsAge; }
13: private:
14: int itsWeight;
15: int itsAge;
16: };
17:
18: void setValue(Animal& theAnimal, int theWeight)
19: {
20: friend class Animal;
21: theAnimalitsWeight = theWeight;
22: }
23:
24: int main()
25: {
26: Animal peppy;
27: setValue(peppy,5):
28: return 0;
29: }
Нельзя помещать объявление friend в функцию. Нужно объявить функцию другом в объявлении класса.
6. Исправьте листинг, приведенный в упражнении 5, и откомпилируйте его.
1: #include <iostream.h>
2:
3: class Animal;
4:
5: void setValue(Animal& , int);
6:
7:
8: class Animal
9: {
10: public:
11: friend void setValue(Animal&, int);
12: int GetWeight()const { return itsWeight; }
13: int GetAge() const { return itsAge; }
14: private:
15: int itsWeight;
16: int itsAge;
17: };
18:
19: void setValue(Animal& theAnimal, int theWeight)
20: {
21: theAnimal.itsWeight = theWeight;
22: }
23:
24: int main()
25: {
26: Animal peppy;
27: setValue(peppy,5);
28: return 0;
29: }
7. Жучки: что неправильно в этой программе?
1: #include <iostream.h>
2:
3: class Animal;
4:
5: void setValue(Animal& , int):
6: void setValue(Animal& , int.int);
7:
8: class Animal
9: {
10: friend void setValue(Animal& ,int):
11: private:
12: mt itsWeight;
13: int itsAge;
14: };
15:
16: void setValue(Animal& theAnimal, int theWeight)
17: {
18: theAnimal.itsWeight = theWeight;
19: }
20:
21:
22: void setValue(Animal& theAnimal, int theWeight, int theAge)
23: {
24: theAnimal.itsWeight = theWeight:
25: theAnimal.itsAge = theAge;
26: }
27:
28: int main()
29: {
30: Animal peppy;
31: setValue(peppy,5);
32: setValue(peppy,7,9);
33: return 0:
34: }
Функиия setValue(Animal& ,int) была объявлена дружественной, но перегруженная
функция setValue(Animal& ,int,int) не была объявленадружественной.
8. Исправьте листинг, приведенный в упражнении 7, и откомпилируйте его.
1: #include <iostream.h>
2:
3: class Animal;
4:
5: void setValue(Animal& , int);
6: void setValue(Animal& , int.int);
7:
8: class Animal
9: {
10: friend void setValue(Animal& ,int);
11: friend void setValue(Animal& ,int.int): // изменение!
12: private:
13: int itsWeight;
14: int itsAge;
15: };
16:
17: void setValue(Animal& theAnimal, int theWeight)
18: {
19: theAnimal.itsWeight = theWeight;
20: }
21:
22:
23: void setValue(Animal& theAnimal, int theWeight, int theAge)
24: {
25: theAnimal.itsWeight = theWeight;
26: theAnimal.itsAge = theAge;
27: }
28:
29: int main()
30: {
31: Animal peppy;
32: setValue(peppy.5);
33: setValue(peppy,7,9);
34: return 0;
35: }