Философия Java


Взаимозаменяемые объекты с полиморфизмом - часть 3


Если вы пишете метод в Java (скоро вы выучите как это делать):

void doStuff(Shape s) { s.erase(); // ...

s.draw(); }

Эта функция говорит любой Форме, так что это не зависит от специфического типа объекта, который рисуется и стирается. Если в некоторой части программы мы используем функцию doStuff( )

:

Circle c = new Circle(); Triangle t = new Triangle(); Line l = new Line(); doStuff(c); doStuff(t); doStuff(l);

Вызов doStuff( ) автоматически работает правильно, не зависимо от точного типа объекта.

Это, фактически, красивый и удивительный фокус. Рассмотри строку:

doStuff(c);

Что случится здесь, если в функцию будет передана Окружность, которая ожидает Форму. Так как Окружность является Формой, это можно трактовать, как передачу Формы в doStuff( ). Так что любое сообщение, которое может послать doStuff( ) Форме, Окружность может принять. Так что это полностью безопасно и самое логичное, что можно сделать.

Мы называем этот процесс, когда наследуемый тип трактуется как базовый, обратное преобразование (upcasting). Название преобразование (cast) использовалось в смысле преобразования к шаблону, а Обратное (up) исходит от способа построения диаграммы наследования, которая обычно упорядочена так: базовый тип вверху, а наследуемые классы развертываются вниз. Таким образом, преобразование к базовому типу - это перемещение вверх по диаграмме наследования: “обратное преобразование”.


Объектно-ориентированное программирование содержит кое-где обратное преобразование, поскольку, так как вы отделяете себя от знания точного типа, вы работаете с этим. Посмотрите на код doStuff( ):

s.erase(); // ...

s.draw();

Заметьте, что это не значит сказать: “Если ты Окружность, сделай это, если ты Квадрат, сделай то и т.д.” Если вы пишете код такого рода, который проверяет все возможные типы, которыми может быть Форма, это грязный способ и вы должны менять его всякий раз, когда добавляете новый сорт Формы. Здесь вы просто говорите: “Ты - Форма, я знаю, что ты можешь стирать erase( ) и рисовать draw( ) сама. Сделай это и правильно позаботься о деталях.”




Начало  Назад  Вперед



Книжный магазин