- •1.Объектно-ориентированные методы. Дайте определение объектно-ориентированного программирования, объектно-ориентированного проектирования и объектно-ориентированного анализа.
- •2. Сфера применения, преимущества и недостатки объектных методов.
- •3. Эволюция объектно-ориентированных языков программирования.
- •4. Эволюция методов объектно-ориентированного проектирования.
- •5. Объект как фундаментальное понятие объектно-ориентированных методов. Дайте определение состояния, поведения и уникальной идентичности объектов.
- •6. Уникальная идентичность объектов. Идентичность объектов Вселенной. Идентичность объектов в объектно-ориентированных моделях. Примеры.
- •7. Понятие класса в объектно-ориентированных методах. Дайте определение поведения и структуры класса. Понятие контракта и реализации класса. Обозначение класса в uml. Примеры.
- •17. Понятие полиморфизма. Классификация типов полиморфизма по Вегнеру.
- •26 Сравнение абстрактных классов и интерейсов:
- •27 Принцип подстановки Барбары Лисков. «Правильное» построение иерархий классов:
- •25. Наследование интерфейсов. Преимущества и недостатки. Объясните реализацию интерфейсов на примере интерфейса iAny:
- •28 Сравнение иерархий агрегации (is part of) и наследования (is kind of):
- •29 Делегирование методов (функциональный подход) и паттерн проектирования «Шаблонный метод»:
- •Применимость
- •30 Принцип инверсии управления в проектировании классов (IoC – Inversion of Control):
- •Управление доступом к членам класса. Члены-данные и члены-функции класса. Доступ к элементам класса. Синтаксис. Пример.
- •Специальные члены-функции класса. Синтаксис. Пример.
- •37. Конструктор класса. Виды конструкторов. Синтаксис. Пример.
- •38. Деструктор класса. Правила написания деструктора. Синтаксис. Пример.
- •39. Друзья класса. Дружественные функции и классы. Правила относительно друзей. Пример.
- •40. Оператор присваивания. Назначение. Синтаксис. Пример.
- •43. Статические (static) члены класса. Назначение. Синтаксис. Пример.
- •Проектирование классов с методами без побочных эффектов.
- •Проектирование по контракту: пред и постусловия, инвариант класса.
- •Понятие метаклассов.Поддержка метаклассов в различных языках программирования.
17. Понятие полиморфизма. Классификация типов полиморфизма по Вегнеру.
Полиморфизм (Polymorphe греч.) Дословно - множественность форм. Способность объекта или оператора ссылаться на объекты разных классов на стадии выполнения. Таким образом, полиморфные сообщения могут интерпретироваться по-разному, если они получены разными объектами или в разных контекстах.
Операция, которая изображает объект на экране в некотором контексте, может быть объявлена виртуальной в базовом классе и переопрелена подклассами. Когда эту операцию вызывают для какого-то объекта, программа определяет, что, собственно, выполнять. Эта особенность называется полиморфизмом: одно и то же имя может означать объекты разных типов, но, имея общего предка, все они имеют и общее подмножество операций, которые можно над ними выполнять. Противоположность полиморфизму называется мономорфизмом; он характерен для языков с сильной типизацией и статическим связыванием (Ada). Впервые идею полиморфизма описал Страчи, имея в виду возможность переопределять смысл символов, таких, как "+", сообразно потребности. В современном программировании мы называем это перегрузкой. Страчи говорил также о параметрическом полиморфизме, который мы сейчас называем просто полиморфизмом.
Полиморфизм возникает там, где взаимодействуют наследование и динамическое связывание. При полиморфизме связь метода и имени определяется только в процессе выполнения программ. Наследование без полиморфизма возможно, но не очень полезно (операции жестко задаются на стадии компиляции).
Вегнер предложил следующую классификацию полиморфизма:
Специальный полиморфизм |
Универсальный полиморфизм |
Перегрузка (времени компиляции) |
Параметрический (времени компиляции) |
Приведение типов (времени компиляции или времени выполнения) |
Полиморфизм включения (наследования или времени выполнения) |
18. Специальный полиморфизм. Перегрузка функций и операторов в С++. Порядок поиска подходящей функции при перегрузке. Примеры.
Специальный полиморфизм допускает специальную реализацию для данных каждого типа. Например, используемая функцией сортировки, функция сравнения должна быть определена по-разному для чисел, строк, т. е. она является специально полиморфной.
Перегрузка имён функций: Возможность определения одного имени для операции, выполняемой с различными типами.
…
function print (a, b : Byte) : string; Overload;// либо при описании класса begin if a > b then ShowMessage (a,'>',b) else ShowMessage (a,'<=',b); end; function print (a, b : Integer) : string; Overload; begin if a > b then ShowMessage (a,'>',b) else ShowMessage (a,'<=',b); end;
procedure TForm1.FormCreate(Sender: TObject); begin
print (10,100)
print (23.45,23,14);
end;
…
Перегрузка операторов: Возможность использования одного символа для выполнения семантически несвязанных операций. Например, «+» для суммирования целых чисел и матриц. В Делфи перегружать опреторы нельзя
Class operator <оператор>(параметры)<возвращаемый тип>
Порядок поиска подходящей функции.
Точное совпадение типов.
Соответствие, достигаемое «продвижением» интегральных типов (например, bool à char, char à int, int àunsigned)
Соответствие, достигаемое путём стандартных преобразований (int àreal, real à int, real à long double).
Соответствие, достигаемое при помощи преобразований, определяемых пользователем.
Соответствие за счёт многоточий (…).
19. Специальный полиморфизм. Приведение типов. Явные и неявные преобразования типа в С++. Примеры.
Явные:
Procedure Depertment (NodeObj:TObject);
Var Dep:TDepartment;
begin
if (NodeObj is TDepartment) then
begin
Dep:=TDepartments.Create;
Dep := NodeObj as TDepartment;
…
End;
…
End;
Неявное преобразование – присваивание объекта одного типа объекту другого типа. Числовой переменной можно присвоить любое числовое значение, входящее в допустимый диапазон данного типа. Тип char может использоваться всюду, где допускается использование int. Значение с плавающей точкой может быть присвоено любой переменной с плавающей точкой, имеющей ту же или большую точность.
20. Универсальный полиморфизм. Наследование. Проблемы классификации. Получение иерархии классов. Одиночное наследование в С++.
Универсальный полиморфизм —противоположность специальному полиморфизму, объединяет параметрический полиморфизм и наследование в один вид полиморфизма.
Наследование - возможность класса наследовать структуру и поведение другого класса (для одиночного наследования) или нескольких классов (множественное наследование).
Класс, структура и поведение которого наследуются, называется суперклассом. Производный от суперкласса класс называется подклассом. Это означает, что наследование устанавливает между классами иерархию общего и частного. В этом смысле подкласс является более специализированным классом, а суперкласс более общим. При Самый общий класс в иерархии классов называется базовым. В большинстве приложений базовых классов бывает несколько, и они отражают наиболее общие абстракции предметной области. В некоторых языках программирования определен базовый класс самого верхнего уровня. В языке Delphi эту роль играет класс TObject. В большинстве языков допускается не только наследование методов суперкласса, но также добавление новых и переопределение существующих методов.
Проблемы классификации: если у нас есть класс "собака", то в описании классов записано, что каждый объект этого класса также принадлежит классу "млекопитающее", каждое млекопитающее также принадлежит классу "животное", каждое животное также принадлежит некоему базовому классу "объект". В результате в нашей программе каждая собака автоматически является ещё и млекопитающим, животным и объектом. Использование наследования слишком жёстко и однозначно определяет классификацию объектов. В частности, имея набор классов "объект" – "животное" – "млекопитающее" – "собака" пространство нашего манёвра сужено тем фактом, что собака обязана быть живым существом. Появление среди объектов собаки - робота, не являющейся живым существом, создаст определённые проблемы.
Пример:
TA80Gas = class(TGas)
public
Constructor Create;
end;
TGas = class
protected
Price: Currency;
Name: String;
Public
Constructor Create;
function GetName: String;
function GetPrice: Currency;
end;
21. Универсальный полиморфизм. Наследование. Статические и виртуальные функции в С++. Абстрактные классы в С++. Примеры.
Универсальный полиморфизм —противоположность специальному полиморфизму, объединяет параметрический полиморфизм и наследование в один вид полиморфизма.
Методы, определенные в классе, могут быть статическими, виртуальными или абстрактными. Различие между вызовом статического метода и виртуального метода заключается в том, что в первом случае компилятору заранее известна связь объекта с методом, и он устанавливает ее на этапе компиляции. Такое связывание называется ранним. Во втором – компилятор как бы откладывает решение до момента выполнения программы. Это позднее связывание. Каждый тип объекта, содержащий виртуальные методы, имеет таблицу виртуальных методов (ТВМ) – сегмент данных, содержащий размер типа объекта и для каждого виртуального метода указатель кода, исполняющий данный метод. Например, пусть у нас имеется описание родительского класса TCircle и его потомка TEllipse, содержащих одноименный метод. В соответствии с принципом полиморфизма в операторе TCircle.Square; вызывается метод, описанный в классе TCircle, а в операторе TEllipse.Square; вызывается метод, описанный в классе TEllipse. По умолчанию все методы, описанные в классе, являются статическими. Для обьявления виртуального метода в родительском классе необходимо использовать зарезервированное слово virtual. В классе-потомке в загаловке замещающего метода должно быть указано зарезервированное слово override. Кроме прочего виртуальный метод позволяет вызвать родительскому классу метод дочернего.
Базовый класс называется абстрактным, если он не содержит реализацию виртуальной функции. Абстрактный класс – класс, содержащий хотя бы 1 реалтзованный метод. Основное предназначение абстрактных методов-быть родоначальником иерархий конкретных методов в классах-потомках.
22. Интерфейсы. Интерфейсы в С++. Отличие наследования интерфейсов от множественного наследования. Примеры.
Отличие наследования интерфейсов от множественного наследования (наследование реализации):
Наследование реализации означает, что класс происходит от базового класса и получает все его поля-члены и функции. Наследник полностью реализует базовый класс, если только явно не указано, что используются виртуальные функции, которые могут быть переопределены наследником. Такое наследование полезно когда надо добавить функциональность существующему классу или же когда несколько классов имеют частично схожую функциональность.
Наследование интерфейсов означает, что класс наследует только сигнатуру функций, но не наследует реализации. Такой тип полезен, когда надо специфицировать несколько классов одним интерфейсом. Говорят, что подкласс поддерживает интерфейс суперкласса. Реализация унаследованных операций откладывается на более позднее время.
В Delphi все интерфейсы являются наследниками IUnknown (или IInterface)
type // Определение интерфейса IVehicle = Interface(IInterface) function GetAge : Integer; function GetMiles : Integer; property age : Integer read GetAge; property miles : Integer read GetMiles; end; // Выполнение этого интерфейса в классе car // Обратите внимание, что TInterfaceObject определяет для нас // QueryInterface, _AddRef, _Release функции TCar = Class(TInterfacedObject, IVehicle) private fAge, fMiles : Integer; fCarType : string; function GetAge : Integer; function GetMiles : Integer; public property age : Integer read GetAge; property miles : Integer read GetMiles; property carType : string read fCarType;
published constructor Create(age, miles : Integer; carType : string); end;
implementation
constructor TCar.Create(age, miles: Integer; carType: string); begin fAge := age; fMiles := miles; fCarType := carType; end;
23. Универсальный полиморфизм. Наследование. Проблема «среза». Примеры на С++.
Проблема среза – вызов методов определенных только в классе наследнике через указатель на базовый класс. Решение – прямое приведение типа для указателя.
Transport = class
public
function Speed:real; virtual;
end;
Airtransport = class (Transport)
public
function Speed:real; override;
function Altitude:real;
end;
implementation
Procedure…
var
t: Transport;
c:real;
begin
t:= Airtransport.Create;
c:=t.speed;
c:=t. Altitude; //проблема «среза», решение: c:=(t as Airtransport).Altitude;
end;
// потомок может использовать все ф-ии родителя а родитель не может использовать ф-ии потомка если они не виртуальные
24. Множественное наследование в С++. Проблемы множественного наследования. Варианты решений проблем множественного наследования.
Интерфейсы являются специальной разновидностью полностью абстрактных классов. То есть таких классов, в которых вообще нет реализованных методов - все методы абстрактные. Полей данных в них также нет, но можно задавать константы (неизменяемые переменные класса). Отсутствие в интерфейсах полей данных и реализованных методов снимает почти все проблемы множественного наследования.
Множественное наследование. Оно означает, что у класса может быть не один непосредственный прародитель, а два или более.
Но при множественном наследовании классов возникает ряд трудно разрешимых проблем. Например, наследование ненужных полей и методов, конфликты совпадающих имен из разных ветвей наследования. В частности, так называемое ромбовидное наследование, когда у класса A наследники B и C, а от них наследуется класс D. Поэтому класс D получает поля и методы, имеющиеся в классе A, в удвоенном количестве – один комплект по линии родителя B, другой – по линии родителя C.
Создатели языка Java, во многом базирующегося на С++, отказались от множественного наследования, заменив его менее рискованной реализацией абстрактных интерфейсов (implements) и разрешив обычное наследование (extends) только одного класса.
