Програмування С, С++теорія та практика (частина 2)
2.11 Контейнерні класи.
Класи, що містять у своєму протоколі один або декілька об'єктів або покажчиків на об'єкти, носять назву контейнерних класів (сіазз сопґаіпегз). В даному випадку має місце відношення між класами типу "містить". Найчастіше таку побудову протоколів класів підказує логіка програми, адже не завжди лише за допомогою успадкування вдається адекватно відобразити всю сукупність складних взаємовідношень між класами.
В якості прикладу розглянемо наочний приклад з життя - протокол деякого класу Ноизе. Протокол цього класу містить поля - об'єкти класу Коот, який у свою чергу - поля класу Ригпіґиге. Створивши такий проект, можна сказати, що будинок Ноизе має кімнати Коот, в яких є меблі Ригпіґиге.
#іпс1ийе<іоз'Ьгеат.Ь>
#іпс1ийе<з'Ьгіпд.Ь>
/ / протокол класу Еигпі'Ьиге с1азз Еигпі'Ьиге {
рг^а^е:
сЬаг моой'Ьуре[20]; сЬаг £игп^уре[25]; риЬ1іс:
Еигпі^иге(сЬаг* моой, сЬаг*зог^)
{
сои£ «"Сопз'Ьгис'Ьог о£ £игпі^иге\п"; з^гсру(моой^уре, моой); з'Ьгсру (зог£, £игп^уре);
£гіепй оз£геат& орега'Ьог<<(оз'Ьгеат& о, Еигпі'Ьигеі
а£игп);
};
оз^геат& орега'Ьог<<(оз'Ьгеат& о, Еигпі'Ьигеі а£игп)
{
сои£<<"Еигпі £иге із"<<а£игп.£игп'Ьуре<<"\п"; сои^<<"Еигпі^иге із тайе о£ "<<а£игп.моой'Ьуре<<"\п";
}
// протокол класу К.оот с1азз К.оот {
рг^а^е:
Еигпі'Ьиге £игп1, £игп2; ипзідпей 1епд£Ь, мій'ЬЬ; сЬаг ехроизег[50];
Коот(Еигпі^иге р1, Еигпі'Ьиге р2, ипзідпей 1,ипзідпей м, сЬаг* ехр):
£игп1(р1), £игп2(р2), 1епд£Ь(1), мій^Ь(м)
{
сои'Ь<<"Сопз'Ьгис'Ьог о£ гоот\п" ; з^гсру(ехроизег, ехр);
}
£гіепй оз^геат& орега'Ьог<<(оз'Ьгеат& о,
Коот& аК.оот) ;
};
оз^геат& орега'Ьог<<(оз'Ьгеат& о, Коот& аК.оот)
{
сои^<<"Ьепд^Ь із "<<аК.оот.1епд'ЬЬ<<"\п"; сои^<<"ЇТій^Ь із "<<аК.оот.мій'ЬЬ<<" \п";
сои^<<"Ехрозе о£ гоот ---- "<<аК.оот.ехроизег<<"\п";
сои^<<"Еигпі^иге 1---- "<<аК.оот.£игп1<<"\п";
сои^<<"Еигпі^иге 2---- "<<аК.оот.£игп2<<"\п";
}
// протокол класу Ноизе с1азз Ноизе {
рг^а^е:
К.оот г1, г2,г3;
£1оа£ ргісе; ипзідпей здиаге; риЬ1іс:
Ноизе (К.оот аг1, К.оот аг2, К.оот аг3, £1оа£ аргісе, ипзідпей агеа): г1(аг1), г2(аг2), г3(аг3), ргісе(аргісе), здиаге(агеа)
{
сои£<< " Ми1'Ьір1е сопз'Ьгис'Ьог £ог Ьоизе\п" ;
£гіепй оз^геат& орега'Ьог<<(оз'Ьгеат& о,
Ноизе& аНоизе);
};
оз^геат& орега'Ьог<<(оз'Ьгеат& о, Ноизе& аНоизе)
{
сои^<<"Ргісе із "<<аНоизе.ргісе<<"\п"; сои^<<"Агеа із "<<аНоизе.здиаге<<"\п";
сои^<<"Коот 1 --- "<<аНоизе.г1<<"\п";
сои^<<"Коот 2 --- "<<аНоизе.г2<<"\п";
сои^<<"Коот 3 --- "<<аНоизе.г3<<"\п";
}
Якою буде послідовність виклику конструкторів при створенні об'єкту класу Ноизе? Спочатку буде проведено ініціалізацію усіх полів- об'єктів у протоколі класу у тому порядку, як вони оголошені. Тільки після цього ініціалізуватиметься сам клас, що містить ці поля. Оголошення змінної Ноизе ту_коизе(тоот1, гоот2, 5500.00, 50) спричинить виклик довгого ланцюга конструкторів. Першими викликатимуться конструктори класу Ригпіґиге, після чого Коот, і насамкінець, Ноизе.
Прикладами контейнерних класів можуть служити класи користувача, що описують масиви, лінійні списки або стеки. Характерно, що для кожного типу такого контейнеру можна визначити стандартні методи роботи з його елементами, які не залежать від конкретного типу даних, що зберігається у контейнері, тому один і той самий вид контейнеру можна використовувати для зберігання та обробки даних різних типів. Ця можливість реалізується за допомогою шаблонів класів, про що вже йшла вище мова у відповідному розділі. На сьогодні є добре відомою стандартна Сі++-бібліотека шаблонів $ТЬ(8ґапСагґ Тетріаґе ЬіЬгагу), яка містить основні структури даних для написання програм, такі як вектори, черги, різновиди списків, множини та словники. На жаль, з причин обмеженого об'єму, її розгляд не входить до переліку тем даного посібника.
12 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86
