Программирование >>  Программирование на языке c++ 

1 ... 8 9 10 [ 11 ] 12 13 14 ... 159


типа. Однако мы может также сказать, что а и b - это объекты класса int. То же самое можно выразить по отношению к новым типам, например:

class my class { ..................... };

где class - это ключевое слово для объявления нового типа, my class - имя нового типа. Теперь my class дополняет фундаментальные типы, такие, как int, float, char и т.п. Описание: my class c,d;

задает объекты end класса my class. Таким образом, а, Ь, с и d - это объекты, и они различаются только классами или типами.

Любой язык программирования определяет не только множество фундаментальных (стандартных или предопределенных) типов, но и множество операций над объектами этих типов, выраженными через соответствующие операторы. Когда мы описываем переменные целого типа а и Ь, мы даже не задумываемся о возможности выполнения различных операций, например:

а=5; Ь=10; а+=Ь; а++; а~;

Мы использовали в этих выражениях операторы, которые определены для целых чисел: присваивание =, увеличение а на значение b +=; инкремент ++; декремент ~. Однако, например, в языке С++ есть и другие операторы, например ->. Если мы запишем выражение

а = а -> Ь;

то оно будет ошибочным, поскольку оператор -> не определен для целых чисел.

Из вышесказанного можно сделать следующие выводы: ф- каждый язык определяет множество стандартных типов и множество операций над этими типами;

ф- если мы хотим построить новые типы, то мы должны определить множество операций над этими типами;

ф- для того чтобы использовать привычный синтаксис (привычный стиль записи выражений), желательно иметь возможность переопределения заданных в языке операторов.

Поясним приведенные выводы примерами. Пусть задано описание:



my class c,d; Рассмотрим выражение c = d;

Его можно понимать по-разному. Стандартно (в языках C/C++) это выражение понимается как копирование значений компонентов-данных объекта d в соответствующие компоненты-данные объекта с. А что будет, если некоторый компонент d - это указатель на динамически выделенную память (пусть, например, такое выделение осуществляется на этапе конструирования объекта d)? Здесь уже возникают серьезные проблемы (рис. 1.6):

ф- указатели обоих объектов end будут адресовать одну и ту же память (т. е. память объекта d). В результате пропадает указатель на память с и, как следствие, мы теряем эту память. Этот процесс называется утечкой памяти (memory leak);

ф- при разрушении объектов end память d освобождается дважды. При этом возникает неисправимая ошибка.

Таким образом, выражение c=d; является привычным для нас. Мы знаем назначение оператора = и нам не нужны дополнительные пояснения. Однако приведенное выражение можно использовать не всегда. Что делать в этом случае? Надо переопределять значение оператора = по отношению к объектам класса my class (что поддерживается механизмами полиморфизма). Причем это надо сделать так:

ф- оператор = должен сохранять свое прежнее значение для стандартных типов, определенных в самом языке, т. е. если операнды (операнд) оператора = имеют стандартные типы, то он используется в прежнем смысле;

ф- оператор = должен задавать новые (разумные) действия для новых типов, т. е. если хотя бы один операнд оператора = имеет новый тип, то этот оператор задает новые действия.

Заметим, что подобная стратегия ведет к расширению, но не к изменению языка.

Пояснения и примеры, касающиеся этого вопроса, приведены в гл. 5.



Объект с

Объект d

динамическая память с

ПЕРЕдТ

c = d; I I

динамическая память d

динамическая память с

->

динамическая память d

1, Потеря памяти

2. Возможное освобождение памяти дважды I!!

Рис. 1. 6. Проблемы, возникающие при присваивании объектов

Доопределение операторов в литературе выражается термином operator overloading [1-3], который можно перевести как перегрузка операторов .

В § 1.5 говорилось о том, что объектно-ориентированный язык поддерживает механизмы наследования (рис. 1.7).

Принцип наследования позволяет:

-ф- выразить общность интерфейса базовых и производных классов;

осуществить развитие и совершенствование программ без изменения того, что уже сделано раньше.

Из рис. 1.7 видно, что в общем случае производный класс больше , чем его базовый класс, в связи с тем, что он может:



1 ... 8 9 10 [ 11 ] 12 13 14 ... 159

© 2006 - 2024 pmbk.ru. Генерация страницы: 0
При копировании материалов приветствуются ссылки.
Яндекс.Метрика