Так, например, если в заданном месте экрана уже отображена какая-то строка и мы хотим изменить положение строки на экране, то мы посылаем объекту новое значение свойства в виде набора нужных координат. Далее свойство автоматически трансформируется в вызов метода, который изменит значение поля координат отображения строки и выполнит действия по уничтожению изображения строки на прежнем месте экрана, а также по отображению строки в новом месте экрана.
Можно выделить несколько преимуществ инкапсуляции.
Преимущество 1. Надежность данных. Можно предотвратить изменение элемента данных, выполнив в свойстве (методе) дополнительную проверку значения на допустимость. Тем самым можно гарантировать надежное состояние объекта.
Преимущество 2. Целостность ссылок. Перед доступом к объекту, связанному с данным объектом, можно удостовериться, что косвенное поле содержит корректное значение (ссылку на экземпляр).
Преимущество 3. Предусмотренные побочные эффекты. Можно гарантировать, что каждый раз, когда выполняется обращение к полю объекта, синхронно с ним выполняется какое-либо специальное действие.
Преимущество 4. Сокрытие информации. Когда доступ к данным осуществляется только через методы, можно скрыть детали реализации объекта. Позднее, если реализация изменится, придется изменить лишь реализацию методов доступа к полям. Те же части программы, которые использовали этот класс, не будут затронуты.
Весьма удобно рассматривать объекты как попытку создания активных данных. Смысл, вкладываемый в слова "объект представляет собой активные данные", основан на объектно-ориентированной парадигме выполнения операций, состоящей в посылке сообщений. В посылаемых объекту сообщениях указывается, что мы хотим, что бы он выполнил. Так, например, если мы хотим вывести на экране строку, то мы посылаем объекту строки сообщение, чтобы он изобразил себя. В этом случае строка — это уже не пассивный кусок текста, а активная единица, знающая, как правильно производить над собой различные действия.
Одна из фундаментальных концепций ООП — это понятие наследования классов, устанавливающее между двумя классами отношения "родитель-потомок".
Наследование — отношение самого высокого уровня и играет важную роль на стадии проектирования. Наследование — это определение класса и затем использование его для построения иерархии производных классов, причем каждый класс-потомок наследует от класса-предка интерфейс всех классов-предков в виде доступа к коду их методов и данным. При этом, возможно, переопределение или добавление как новых данных, так и методов.
Класс-предок — это класс, предоставляющий свои возможности и характеристики другим классам через механизм наследования. Класс, который использует характеристики другого класса посредством наследования, называется его классом-потомком.
Итак, наследование проявляется в том, что любой класс-потомок имеет доступ или, другими словами, наследует практически все ресурсы (методы, поля и свойства) родительского класса и всех предков до самого верхнего уровня иерархии.
Рассмотрим, как информация, содержащаяся в классе-потомке, может переопределять информацию, наследуемую от предков. Очень часто при реализации такого подхода метод, соответствующий подклассу, имеет то же имя, что и соответствующий метод в родительском классе. При этом для поиска метода, подходящего для обработки сообщения, используется следующее правило. Поиск метода, который вызывается в ответ на определенное сообщение, начинается с методов, принадлежащих классу получателя. Если подходящий метод не найден, то поиск продолжается до родительского класса. Поиск продвигается вверх по цепочке родительских классов до тех пор, пока не будет найден нужный метод или пока не будет исчерпана последовательность родительских классов. В первом случае выполняется найденный метод, во втором выдается сообщение об ошибке. Во многих языках программирования уже на этапе компилирования, а не при выполнении программы определяется, что подходящего метода нет вообще и выдается сообщение об ошибке.
Семантически наследование описывает отношение типа "is-a". Например, медведь есть млекопитающее, дом есть недвижимость и "быстрая сортировка" есть сортирующий алгоритм. Таким образом, наследование порождает иерархию "обобщение — специализация", в которой подкласс представляет собой специализированный частный случай своего суперкласса. "Лакмусовая бумажка" наследования — обратная проверка: так, если В не есть А, то В не стоит производить от А.
Повторное использование — это использование в программе класса для создания экземпляров или в качестве базового для создания нового класса, наследующего часть или все характеристики родителя. Порождая классы от базовых, вы эффективно повторно используете код базового класса для собственных нужд. Повторное использование сокращает объем кода, который необходимо написать и оттестировать при реализации программы, что сокращает объемы труда.
Таким образом, наследование выполняет в ООП несколько важных функций:
• моделирует концептуальную структуру предметной области;
• экономит описания, позволяя использовать их многократно для задания разных классов;
• обеспечивает пошаговое программирование больших систем путем многократной конкретизации классов.
Ряд языков, например Object Pascal, описание которого дается в приложении 4, поддерживает модель наследования, известную как простое наследование и которая ограничивает число родителей конкретного класса одним. Другими словами, определенный пользователем класс имеет только одного родителя. Схема иерархии классов в этом случае представляет собой ряд одиночно стоящих деревьев (hierarchical classification).
Более мощная модель сложного наследования, называемая множественным наследованием, в которой каждый класс может, в принципе, порождаться сразу от нескольких родительских классов, наследуя поведение всех своих предков. Множественное наследование не поддерживается в Delphi, но поддерживается в Visual C++ и ряде других языков. При множественном наследовании составляется уже не схема иерархии, а сеть, которая может включать деревья со сросшимися кронами.
Обычно если объекты соответствуют конкретным сущностям реального мира, то классы являются абстракциями, выступающими в роли понятий. Между классами, как между понятиями, существует иерархическое отношение конкретизации, связывающее класс с классом-потомком. Это отношение реализуется в системах ООП механизмом наследования. Наследование — это способность одного класса использовать характеристики другого.
Наследование позволяет практически без ограничений последовательно строить и расширять классы, созданные вами или кем-то еще. Начиная с самых простых классов можно создавать производные классы по возрастающей сложности, которые не только легки при отладке, но и просты по внутренней структуре.
Множественное наследование многие аналитики считают "вредным" механизмом, приводящим к сложно разрешимым проблемам проектирования и реализации. В языках с отсутствующим множественным наследованием целей множественного наследования достигают агрегированием объектов с дополнительным делегированием полномочий.
На агрегировании основана работа таких систем визуального программирования, как Delphi, C++ Builder. В этих системах имеется порождающий объект пользователя класс-форма (пустое окно Windows). Системы обеспечивают подключение к форме через указатели нужных пользователю объектов, например кнопок, окон редакторов и т. д. При перерисовке формы на экране монитора как бы одновременно с ней перерисовываются изображения агрегированных объектов. Более того, при активизации формы агрегированные объекты также становятся активными: кнопки начинают нажиматься, а в окна редакторов можно начинать вводить информацию.