Студопедия
Случайная страница | ТОМ-1 | ТОМ-2 | ТОМ-3
АвтомобилиАстрономияБиологияГеографияДом и садДругие языкиДругоеИнформатика
ИсторияКультураЛитератураЛогикаМатематикаМедицинаМеталлургияМеханика
ОбразованиеОхрана трудаПедагогикаПолитикаПравоПсихологияРелигияРиторика
СоциологияСпортСтроительствоТехнологияТуризмФизикаФилософияФинансы
ХимияЧерчениеЭкологияЭкономикаЭлектроника

Наследование

Читайте также:
  1. I. Наследование доли в уставном капитале общества с ограниченной ответственностью
  2. Абстрактые классы, виртуальные методы. Наследование и замещение методов.
  3. Билет №20. Аллельные гены. Наследование признаков при взаимодействии аллельных генов. Примеры. Множественный аллелизм. Механизм возникновения.
  4. Билет №21. Неаллельные гены. Наследование признаков при взаимодействии неаллельных генов. Примеры.
  5. Глава 2. НАСЛЕДОВАНИЕ ПО ЗАВЕЩАНИЮ
  6. Глава 3. НАСЛЕДОВАНИЕ ПО ЗАКОНУ
  7. Глава 5. НАСЛЕДОВАНИЕ ПО ЗАКОНУ

Наследование и спецификаторы доступа

 

Прежде всего необходимо коснуться терминологии. Класс, который наследуется другим классом, называются базовым классом. Иногда его также называют родительским классом. Класс, выполняющий наследование, называется производным классом или потомком.

 

Спецификаторы доступа

 

В С++ члены класса классифицируются в соответствии с правами доступа на следующие три категории: публичные (public), частные (private) и защищённые (protected). Любая функция программы имеет доступ к публичным членам. Доступ к частному члену имеют только функции-члены класса или функции-друзья класса. Защищённые члены аналогичны частным членам. Разница между ними проявляется только при наследовании классов.

 

Спецификатор доступа при наследовании базового класса

 

От того, с каким спецификатором доступа объявляется наследование базового класса, зависит статус доступа к членам производного класса. Общая форма наследования классов имеет следующий вид:

 

class имя_класса: доступ имя_класса {

};

 

Здесь доступ определяет, каким способом наследуется базовый класс. Спецификатор доступ может принимать три значения – private, public, protected. В случае, если спецификатор доступ опущен, то по умолчанию подразумевается на его месте спецификатор public. Если спецификатор доступ принимает значение public, то все публичные и защищённые члены базового класса становятся соответственно публичными и защищёнными членами производного класса. Если доступ private, то все публичные и защищённые члены базового класса становятся частными членами производного класса. Если спецификатор доступа protected, то все публичные и защищённые члены базового класса становятся защищёнными членами производного класса. Рассмотрим пример:

 

Листинг 1

 

#include <iostream>

using namespace std;

 

class X {

protected:

int i;

int j;

public:

void get_ij(){

cout << "Enter two numbers ";

cin >> i >> j;

}

void put_ij(){ cout << i << " " << j << "\n";}

};

 

// В классе Y, i и j класса X становятся защищёнными членами

class Y: public X {

int k;

public:

int get_k(){ return k;}

void make_k(){ k=i*j;}

};

 

// Класс Z имеет доступ к i и j класса X, но не к

// k класса Y, поскольку он является частным

class Z: public Y {

public:

void f();

};

 

// i и j доступны отсюда

void Z::f()

{

i=2;

j=3;

}

 

int main()

{

Y var;

Z var2;

 

var.get_ij();

var.put_ij();

var.make_k();

cout << var.get_k();

cout << "\n";

 

var2.f();

var2.put_ij();

 

return 0;

}

Поскольку класс Y наследует класс X со спецификатором доступа public, то защищённые элементы класса X становятся защищёнными элементами класса Y. Это означает, что они могут далее наследоваться классом Z, и эта программа будет откомпилирована и выполнена корректно. Однако, если изменить статус X при объявлении Y на private, то класс Z не имеет доступа к i, j и функциям get_ij() и put_ij(), поскольку они стали частными членами Y.

 

Конструкторы и деструкторы производных классов

 

Как базовый класс, так и производный класс могут иметь конструкторы. Когда базовый класс имеет конструктор, этот конструктор исполняется перед конструктором производного класса.

Конструкторы вызываются в том же самом порядке, в каком классы следуют один за другим в иерархии классов. Поскольку базовый класс ничего не знает про свои производные классы, то его инициализация может быть отделена от инициализации производных классов и производится до их создания, так что конструктор базового класса вызывается перед вызовом конструктора производного класса.

В противоположность этому деструктор производного класса вызывается перед деструктором базового класса.

 

Передача параметров в базовый класс

 

Когда базовый класс имеет конструктор с аргументами, производные классы должны передавать базовому классу необходимые аргументы. Для этого используется расширенная форма конструкторов производных классов.

 

порождённый_конструктор(список_аргументов): базовый1(список_аргументов), базовый2(список_аргументов), …, базовыйN(список_аргументов)

{

}

 

Здесь под базовый1, базовый2, …, базовыйN обозначены имена базовых классов, наследуемые производным классом. Обратим вниманием, что с помощью двоеточия конструктор производного класса отделяется от списка конструкторов базового класса. Список аргументов, ассоциированный с базовыми классами, может состоять из констант, глобальных переменных или параметров конструктора производного класса.

 

Указатели и ссылки на производные типы

 

В общем случае указатель одного типа не может указывать на объект другого типа. Из этого правила есть исключение, которое относится только к производным классов. В С++ указатель на базовый класс может указывать на объект производного класса. Ссылки на базовый класс могут быть использованы для ссылок на объект производного типа.

 

Виртуальные функции

 

Виртуальная функция – это функция, объявленная с ключевым словом virtual в базовом классе и переопределенная в производных классах. Виртуальные функции являются особыми функциями, потому что при вызове объекта производного класса с помощью указателя или ссылки на него С++ определяет во время исполнения программы, какую функцию вызвать, основываясь на типе объекта. Для разных объектов вызываются разные версии одной и той же виртуальной функции. Класс, содержащий одну или более виртуальных функций, называется полиморфным классом.

 

Листинг 2

 

// Небольшой пример использования виртуальных функций

#include <iostream>

using namespace std;

 

class Base {

public:

virtual void who(){// определение виртуальной функции

cout << "Base\n";

}

};

 

class first_d: public Base {

public:

void who(){// определение who применительно к first_d

cout << "First derivation\n";

}

};

 

class second_d: public Base {

void who(){// определение who применительно к second_d

cout << "Second derivation\n";

}

};

 

int main()

{

Base base_obj;

Base *p;

first_d first_obj;

second_d second_obj;

 

p = &base_obj;

p->who();

p = &first_obj;

p->who();

p = &second_obj;

p->who();

 

return 0;

}

Наиболее распространённым способом вызова виртуальной функции служит использование параметра функции.

 

Листинг 3

 

/* Здесь ссылка на базовый класс используется для доступа

к виртуальной функции */

#include <iostream>

using namespace std;

 

class Base {

public:

virtual void who(){// определение виртуальной функции

cout << "Base\n";

}

};

 

class first_d: public Base {

public:

void who(){// определение who применительно к first_d

cout << "First derivation\n";

}

};

 

class second_d: public Base {

void who(){// определение who применительно к second_d

cout << "Second derivation\n";

}

};

 

// использование в качестве параметра ссылки на базовый класс

void show_who(Base &r) {

r.who();

}

 

int main()

{

Base base_obj;

first_d first_obj;

second_d second_obj;

 

show_who(base_obj);

show_who(first_obj);

show_who(second_obj);

 

return 0;

}

 

Задание выполнить задание соответствующего варианта

Номер Задание
1, 9, 17, 25 Создать базовый класс – боеприпас, который должен содержать элемент-данные: калибр и виртуальную функцию, выдающую эти данные на консоль. Создать производные классы – артиллеристское орудие и винтовку, содержащие данные: для орудия - скорострельность, максимальный угол наклона ствола к горизонту (в градусах), длина ствола и число человек в орудийном расчете; для винтовки – скорострельность, размер и вес. Переопределить унаследованную функцию так, чтобы в производных классах она выводила все данные об объектах. Все классы должны быть в ортодоксальной канонической форме. Создать функцию, выдающую на консоль данные об объекте, не имея сведений о том, объектом какого класса является входной параметр.
2, 10, 18, 26 Создать базовый класс – клетку, который должен содержать элементы-данные: число хромосом и виртуальную функцию, выдающую эти данные на консоль. Создать производные классы – одноклеточное и многоклеточное существо содержащие данные: вид (амеба, бактерия и т.п.) для одноклеточного существа, число органов для многоклеточного существа. Создать производные классы для многоклеточного существа – растение и животное содержащие данные высоту и число семян для растения, вес и необходимое количество корма в день для животного. Переопределить унаследованную функцию так, чтобы в производных классах она выводила все данные об объектах. Все классы должны быть в ортодоксальной канонической форме. Создать функцию, выдающую на консоль данные об объекте, не имея сведений о том, объектом какого класса является входной параметр.
3, 11, 19, 27 Создать базовый класс – автомобиль, который должен содержать элементы-данные: число колёс и мощность двигателя, а также виртуальную функцию, выдающую эти данные на консоль. Создать производные классы – автобус и грузовик, содержащие данные: число пассажиров для автобуса, грузоподъёмность для грузовика. Переопределить унаследованную функцию так, чтобы в производных классах она выводила все данные об объектах. Все классы должны быть в ортодоксальной канонической форме. Создать функцию, выдающую на консоль данные об объекте, не имея сведений о том, объектом какого класса является входной параметр.
4, 12, 20, 28 Создать базовый класс – товар, который должен содержать элементы-данные: цену и вес, а также виртуальную функцию, выдающую эти данные на консоль. Создать производные классы – продовольственный товар и бытовая техника, содержащие данные: срок годности для продовольственного товара, адрес гарантийной мастерской для бытовой техники. Переопределить унаследованную функцию так, чтобы в производных классах она выводила все данные об объектах. Все классы должны быть в ортодоксальной канонической форме. Создать функцию, выдающую на консоль данные об объекте, не имея сведений о том, объектом какого класса является входной параметр.
5, 13, 21, 29 Создать базовый класс – потребитель тока, который должен содержать элементы-данные: потребляемую мощность и тип потребляемого тока, а также виртуальную функцию, выдающую эти данные на консоль. Создать производные классы – холодильник и электродвигатель, содержащие данные: тип холодильника и поддерживаемую в холодильной камере температуру для холодильника, максимальное число оборотов для электродвигателя. Переопределить унаследованную функцию так, чтобы в производных классах она выводила все данные об объектах. Все классы должны быть в ортодоксальной канонической форме. Создать функцию, выдающую на консоль данные об объекте, не имея сведений о том, объектом какого класса является входной параметр.
6, 14, 22, 30 Создать базовый класс – звуковоспроизводящая аппаратура, который должен содержать элементы-данные: мощность и диапазон воспроизводимых частот, а также виртуальную функцию, выдающую эти данные на консоль. Создать производные классы – аналоговый магнитофон и проигрыватель компакт-дисков, содержащие данные: скорость движения ленты и максимальный размер бобины для магнитофона, частоту дискретизации для проигрывателя компакт-дисков. Переопределить унаследованную функцию так, чтобы в производных классах она выводила все данные о классах. Все классы должны быть в ортодоксальной канонической форме. Создать функцию, выдающую на консоль данные об объекте, не имея сведений о том, объектом какого класса является входной параметр.
7, 15, 23, 31 Создать базовый класс – корабль, который должен содержать элементы-данные: водоизмещение и максимальную скорость, а также виртуальную функцию, выдающую эти данные на консоль. Создать производные классы – парусник и пароход, содержащие данные: количество мачт и общую площадь парусов для парусника, мощность паровой машины для парохода. Переопределить унаследованную функцию так, чтобы в производных классах она выводила все данные об объектах. Все классы должны быть в ортодоксальной канонической форме. Создать функцию, выдающую на консоль данные об объекте, не имея сведений о том, объектом какого класса является входной параметр.
8, 16, 24, 32 Создать базовый класс – героя компьютерной игры, который должен содержать элементы-данные: живучесть и силу, а также виртуальную функцию, выдающую эти данные на консоль. Создать производные классы – мифическое животное и человека, содержащие данные: скорость передвижения и магические способности (число от 1 до 100) для животного, верность (число от 1 до 100) и удачу (число от 1 до 100) для человека. Переопределить унаследованную функцию так, чтобы в производных классах она выводила все данные об объектах. Все классы должны быть в ортодоксальной канонической форме. Создать функцию, выдающую на консоль данные об объекте, не имея сведений о том, объектом какого класса является входной параметр.

 


Дата добавления: 2015-07-15; просмотров: 95 | Нарушение авторских прав


<== предыдущая страница | следующая страница ==>
в 1 семестре 2013-2014 учебного года| Основная часть отчета

mybiblioteka.su - 2015-2024 год. (0.017 сек.)