| « Интерфейсы в actionscript 2.0. Часть 3. Много – лучше, чем один | Интерфейсы в actionscript 2.0. Часть 1. Внешние модули » |
Интерфейсы в actionscript 2.0. Часть 2. Одинаковое поведение - разная реализация
Наверное самый распространенный случай использования интерфейсов следующий.
В приложении существует некоторое количество объектов, которые обладают одинаковым поведением, но имеют разную реализацию и не подпадают под случай возможности или рациональности наследования их от одного предка. А так случается часто, ведь у наследования, помимо такого плюса как повторное использование кода, существует и минус - бОльшая связанность, чем при использовании интерфейсов. Нерациональное использование наследования может привести к огромной и подчас неуправляемой иерархии классов, которые сложно поддерживать и использовать.
Рассмотрим пример.
Пусть существует графический редактор с различными панелями и модулями. Необходимо сохранять расположение и настройки этих панелей для следующего сеанса работы с пользователем. Система каждый раз при закрытии, опрашивает все панели на предмет сохраняемых данных, а при следующей загрузке раздает данные обратно. В этом случае можно реализовать интерфейс IRestoreable с методами getRestoreData и setRestoreData, которые служат для получения и установки данных в панель или модуль.
Пример интерфейса.
- /**
- * Интерфейс для элементов с восстанавливаемым состоянием.
- * @author J.Nikolaeva
- * @version 20.12.2006
- */
- interface IRestoreable {
- /**
- * Возвращаем данные о состоянии.
- * @return данные о состоянии
- */
- public function getRestoreData():PanelStateData;
- /**
- * Установка данных о состоянии.
- * @param data - данные о состоянии
- * @return ничего
- */
- public function setRestoreData(data:PanelStateData):Void;
- }
Теперь если реализовать данный интерфейс для панелей и модулей редактора, то можно будет общаться с ними единообразно. Например, пусть классы SizePanel и ColorMixerPanel реализуют данный интерфейс. Из следующего примера понятно, в каком русле можно организовать общение главного приложения с ними.
- /**
- * Приложение графический редактор.
- * @author J.Nikolaeva
- * @version 20.12.2006
- */
- class Application {
- private var sizePanel:IRestoreable;
- private var colorMixer:IRestoreable;
- /**
- * Конструктор.
- */
- public function Application() {
- sizePanel = new SizePanel();
- colorMixer = new ColorMixerPanel();
- sizePanel.setRestoreData(new PanelStateData());
- colorMixer.setRestoreData(new PanelStateData());
- }
- }
Какие здесь плюсы?
- Можем общаться со всеми модулями одинаково.
- Получаем ошибки на этапе компиляции, если обращаемся ‘неправильно’ или ‘не к тому’ методу.
- Не ограничиваем модули одним предком.
- Разрешение ситуации, когда модули и панели уже написаны, а функционал сохранения их состояния необходимо добавить только сейчас.
Хочется упомянуть один момент. Понятное дело, что модули и панели редактора могут иметь и другой общий функционал - изменение размера, перемещение, привязка к другой панели. Тогда возможно появление желания сделать общий интерфейс для таких элементов, например, IEditorPanel, в котором определить все необходимые уважающей себя панели методы.
Стоит быть осторожными, так как это может в дальнейшем связать вам руки. Например, только нектором модулям необходимы методы getRestoreData и setRestoreData, но они включены в этот общий интерфейс, по которому происходит все общение системы с панелями. Тогда вы будете вынуждены определить эти методы во всех панелях, хоть и пустыми, что может привести к недоразумениям. А может случится так, что прийдется изменить сигнатуру какого-нибудь метода в интерфейсе, тогда вы будете вынуждены вносить изменения во все элементы, даже в те, где эти методы объявлены пустыми. Более гибким решением может быть использование нескольких интерфейсов, таких как IResizeable, IRelocatable и т. д.
Трекбек адрес этой записи
URL трекбека (щелкните правой кнопкой мыши и скопируйте ссылку)
3 комментариев
Спасибо, поправлю.