Структури і спадковість. Структури і поліморфізм. Абстрактна структура. Перевантаження операторів у структурах. Статичні методи в структурах
У даній темі на прикладах показано можливості структур в сучасному C++, які нічим не поступаються класам. Необхідність застосування структур в сучасному C++ полягає в забезпеченні сумісності з корисними програмами, розробленими в попередні роки на мові C. Часто переписування цих програм заново немає сенсу, оскільки вимагає додаткових часових та людських ресурсів.
Зміст
- 1. Чи підтримують структури спадковість? Приклад
- 2. Чи може структура бути абстрактною? Чи підтримують структури поліморфізм?
- 3. Приклад, що демонструє застосування поліморфізму у структурах
- 4. Перевантаження операторів у структурі. Структура Point. Приклад
- 5. Використання статичних методів та змінних у структурах. Приклад
- Зв’язані теми
Пошук на інших ресурсах:
1. Чи підтримують структури спадковість? Приклад
Так. Структури підтримують спадковість.
У нижченаведеному прикладі демонструється використання успадкованих структур. Базова структура Worker описує дані про працівника: ім’я та вік. Похідна структура WorkerAge містить методи доступу до полів базової структури. Також демонструється:
- доступ з конструктора похідної структури до конструктора базової структури;
- доступ до захищеного (protected) поля базової структури з успадкованої структури;
- використання покажчика this для доступу до поля базової структури.
Як видно з прикладу, у нових версіях C++ структури є спрощеним варіантом класів.
#include <iostream> using namespace std; // Структура, що описує дані про працівника - базова структура struct Worker { private: string name; // внутрішнє поле, ім'я робітника public: // Конструктор Worker(string _name) { name = _name; } // Методи доступу до поля name в структурі string GetName() { return name; } void SetName(string _name) { name = _name; } protected: int age; // захищене поле - вік працівника }; // Успадкована структура від Worker struct WorkerAge :Worker { // Конструктор з 2 параметрами, викликає конструктор базової структури WorkerAge(string _name, int _age) :Worker(_name) { age = _age; } // Конструктор з 1 параметром WorkerAge(int age) :Worker("Noname") { this->age = age; // доступ через покажчик this на дану структуру } // Методи доступу до поля age int GetAge() { return age; } void SetAge(int _age) { age = _age; } }; void main() { // Методи в структурах // 1. Використання структури Worker Worker w(""); // оголосити екземпляр структури, використовується конструктор w.SetName("John"); // доступ до поля name string nm = w.GetName(); cout << nm.c_str() << endl; // 2. Використання структури WorkerAge WorkerAge wa("Micle", 33); cout << wa.GetName().c_str() << endl; cout << wa.GetAge() << endl; }
Результат виконання програми
John Micle 33
⇑
2. Чи може структура бути абстрактною? Чи підтримують структури поліморфізм?
Так може. Це означає, що в сучасних версіях C++ структури підтримують поліморфізм.
⇑
3. Приклад, що демонструє застосування поліморфізму у структурах
Як і класи, структури підтримують поліморфізм. У прикладі демонструється застосування поліморфізму для структур, що реалізують спадковість.
Оголошується 4 структури з іменами A, B, C, D. Ці структури утворюють ієрархію спадковості. Структура з A є базовою для структури B. Структура B є базовою для структури C. Структура C є базовою для структури D.
У кожній структурі реалізовано метод Print(). Структура A є базовою для структур B, C, D. У цій структурі метод Print() оголошений як чиста віртуальна функція. Такий метод не містить тіла методу. Отже, структура A є абстрактною. Відповідно до синтаксису C++, заборонено оголошувати екземпляр структури A, можна оголошувати тільки покажчик або посилання на цю структуру.
Також у прикладі реалізовано метод PrintStruct(), який отримує посилання на базову структуру A і викликає віртуальний метод Print().
У функції main() демонструється застосування поліморфізму в двох аспектах:
- з використанням покажчика на базову структуру;
- з використанням посилання на базову структуру у методі PrintStruct().
#include <iostream> using namespace std; // Структура, що містить чисто віртуальну функцію - абстрактна структура struct A { virtual void Print() = 0; }; // Успадковані структури B, C, D struct B :A { void Print() override { cout << "B.Print()" << endl; } }; struct C :B { void Print() override { cout << "C.Print()" << endl; } }; struct D :C { void Print() override { cout << "D.Print()" << endl; } }; // Метод, що отримує посилання на базову структуру // та викликає метод Print() цієї структури void PrintStruct(A& refA) { refA.Print(); // викликати метод Print() } void main() { // Демонстрація підтримки поліморфізму у структурах // 1. Оголосити внутрішні змінні A* pA; // покажчик на базову структуру A B objB; // екземпляр структури B C objC; // екземпляр структури C D objD; // екземпляр структури D // 1. Виклик методу Print() єдиним способом (інтерфейсом) // з допомогою покажчика, який вказує на різні екземпляри структур pA = &objB; // перенаправити покажчик на екземпляр структури B pA->Print(); // виклик B.Print() pA = &objC; pA->Print(); // виклик C.Print() pA = &objD; pA->Print(); // виклик D.Print() // 2. Передача посилання на структуру A в метод PrintStruct() cout << "-----------------------------------------------------" << endl; pA = &objB; PrintStruct(*pA); // виклик B.Print() PrintStruct(objB); // виклик B.Print() PrintStruct(objC); // виклик C.Print() PrintStruct(objD); // виклик D.Print() }
Результат виконання програми
B.Print() C.Print() D.Print() ----------------------------------------------------- B.Print() B.Print() C.Print() D.Print()
⇑
4. Перевантаження операторів у структурі. Структура Point. Приклад
У структурах, як і в класах, можна використовувати операторні функції, які перевантажують оператори. Нижче наводиться приклад структури Point, в якій реалізовано перевантаження операторів + (додавання) та – (віднімання).
Структура Point оголошує наступні складові:
- загальнодоступні (public) змінні x, y, що визначають координати точки на площині;
- два конструктори, що ініціалізують внутрішні змінні;
- операторну функцію operator+(), яка перевантажує оператор + (додавання);
- операторну функцію operator–(), яка перевантажує оператор – (віднімання);
- метод Print() для виведення інформації про точку.
У функції main() демонструється використання структури Point.
#include <iostream> using namespace std; // Структура, що описує точку на координатній площині struct Point { public: double x, y; // координати точки // Конструктори Point() { x = y = 0; } Point(double _x, double _y) : x(_x), y(_y) { } // Перевантажений оператор + Point operator+(Point& pt) { return Point(x + pt.x, y + pt.y); } // Перевантажений оператор - Point operator-(Point& pt) { return Point(x - pt.x, y - pt.y); } // Перевантажений оператор присвоєння Point operator=(Point pt) { x = pt.x; y = pt.y; return *this; } // Метод виведення інформації про точку void Print(string objName) { cout << objName << ": x = " << x << ", y = " << y << endl; } }; void main() { // Демонстрація використання структури Point Point pt1(2, 8.5); Point pt2(-5.1, 7.5); // Ініціалізація - тест Point pt3 = pt1; pt3.Print("pt3"); // Тест операторної функції operator+() Point pt4 = pt1 + pt2; pt4.Print("pt4"); // Тест операторної функції operator=() Point pt5; pt5 = pt3; pt5.Print("pt5"); // Тест поєднання операторних функцій operator-(), operator+() Point pt6(1, 1); Point pt7(-3, -3); cout << "---------------" << endl; pt6.Print("pt6"); pt7.Print("pt7"); Point pt8 = pt6 - pt7 - pt3 + pt4; // pt8 = (-1.1, 11.5) pt8.Print("pt8"); }
⇑
5. Використання статичних методів та змінних у структурах. Приклад
У структурах можуть використовуватись статичні методи та змінні. У прикладі реалізовано структуру Complex, яка містить статичні методи обчислення суми, різниці, добутку та ділення комплексних чисел. Також у структурі реалізовано метод Print(), який у виводить комплексне число у зручному вигляді.
У функції main() демонструється використання статичних методів класу Complex.
Текст демонстраційної програми типу ConsoleApplication наступний:
#include <iostream> using namespace std; // Структура, що містить статичні методи обробки комплексних чисел struct Complex { // Загальнодоступні статичні методи // Додавання комплексних чисел (a1+b1*i) + (a2+b2*i) static void Add(double a1, double b1, double a2, double b2, double& a, double& b) { a = a1 + a2; b = b1 + b2; } // Віднімання комплексних чисел static void Sub(double a1, double b1, double a2, double b2, double& a, double& b) { a = a1 - a2; b = b1 - b2; } // Множення комплексних чисел static void Mul(double a1, double b1, double a2, double b2, double& a, double& b) { a = a1 * a2 - b1 * b2; b = a1 * b2 + b1 * a2; } // Ділення комплексних чисел static void Div(double a1, double b1, double a2, double b2, double& a, double& b) { double denom = a2 * a2 + b2 * b2; // Перевірка, чи можна коректно поділити два числа if (denom == 0) { a = b = 0; // встановити нульові значення return; } a = (a1 * a2 + b1 * b2) / denom; b = (a2 * b1 - a1 * b2) / denom; } // Виведення інформації про комплексне число static void Print(string text, double a, double b) { // Встановити точність 2 знаки після коми cout.precision(2); cout << text << a; if (b > 0) cout << "+"; cout << b << "*i" << endl; } }; void main() { // Статичні методи в структурі double a1 = 3, b1 = 2.5; double a2 = 7, b2 = -1.8; double a, b; // Вивести перше число Complex::Print("z1 = ", a1, b1); // Вивести друге число Complex::Print("z2 = ", a2, b2); // Обчислити суму, результат в a, b Complex::Add(a1, b1, a2, b2, a, b); Complex::Print("z1 + z2 = ", a, b); // Обчислити різницю Complex::Sub(a1, b1, a2, b2, a, b); Complex::Print("z1 - z2 = ", a, b); // Обчислити добуток Complex::Mul(a1, b1, a2, b2, a, b); Complex::Print("z1 * z2 = ", a, b); // Обчислити ділення комплексних чисел Complex::Div(a1, b1, a2, b2, a, b); Complex::Print("z1 / z2 = ", a, b); }
Результат виконання програми:
z1 = 3+2.5*i z2 = 7-1.8*i z1 + z2 = 10+0.7*i z1 - z2 = -4+4.3*i z1 * z2 = 26+12*i z1 / z2 = 0.32+0.44*i
⇑
Зв’язані теми
- Складені типи даних. Шаблон структури. Структурна змінна. Структури в середовищі CLR. Оголошення та ініціалізація структурної змінної
- Структури. Використання методів у структурах. Конструктори в структурах
⇑