Краткий ответ: Да, это возможно. Но вы должны делать это нарочно, а не случайно (используя финал, абстракцию и дизайн с учетом наследования и т. Д.)
Длинный ответ:
Ну, на самом деле наследование не для «повторного использования кода», это для «специализации» класса, я думаю, что это неверное толкование.
Например, очень плохая идея - создать стек из вектора, просто потому что они похожи. Или свойства из HashTable только потому, что они хранят значения. См. [Действует].
«Повторное использование кода» было скорее «бизнес-представлением» о характеристиках ОО, означая, что ваши объекты легко распределялись между узлами; и были переносимы и не имели проблем предыдущего поколения языков программирования. Это было доказано наполовину. Теперь у нас есть библиотеки, которые можно легко распространять; например, в java файлы jar можно использовать в любом проекте, экономя тысячи часов разработки. У OO все еще есть некоторые проблемы с переносимостью и тому подобными вещами, поэтому веб-сервисы сейчас так популярны (как прежде это был CORBA), но это уже другой поток.
Это один из аспектов «повторного использования кода». Другой эффективно, тот, который имеет отношение к программированию. Но в данном случае это не просто «сохранение» строк кода и создание хрупких монстров, но и проектирование с учетом наследования. Это пункт 17 в ранее упомянутой книге; Пункт 17: Дизайн и документация для наследования или иного запрета. См. [Действующий]
Конечно, у вас может быть класс автомобиля и множество подклассов. И да, подход, который вы упомянули об интерфейсе Car, AbstractCar и CarImplementation, - правильный путь.
Вы определяете «контракт», которого должен придерживаться Автомобиль, и говорите, что это те методы, которые я ожидал бы использовать, говоря об автомобилях. Абстрактный автомобиль, имеющий базовую функциональность, за которую отвечает каждый автомобиль, но оставляющий и документирующий методы подклассов. В Java вы делаете это, помечая метод как абстрактный.
Если вы поступите таким образом, с «хрупким» классом не возникнет проблем (или, по крайней мере, разработчик сознателен или угроза), и подклассы завершают только те части, которые ему разрешены.
Наследование - это больше, чтобы «специализировать» классы, таким же образом Truck является специализированной версией Car, а MosterTruck специализированной версией Truck.
Он не имеет смысла создавать подкласс «ComputerMouse» из автомобиля только потому, что у него есть колесо (колесо прокрутки), как у автомобиля, он движется и имеет колесо ниже только для сохранения строк кода. Он принадлежит к другому домену и будет использоваться для других целей.
Способ предотвращения наследования "реализации" в языке программирования с самого начала, вы должны использовать ключевое слово final в объявлении класса, и таким образом вы запрещаете подклассы.
Подклассы не являются злом, если они сделаны специально. Если это сделано неосторожно, это может стать кошмаром. Я бы сказал, что вы должны начать как можно более приватно и «окончательно», а при необходимости сделать вещи более публичными и расширяемыми. Это также широко объясняется в презентации «Как создавать хорошие API и почему это важно». См. [Good API]
Продолжайте читать статьи, и со временем и практикой (и большим терпением) эта вещь прояснится. Хотя иногда вам просто нужно выполнить работу и скопировать / вставить некоторый код: P. Это нормально, пока вы сначала стараетесь делать это хорошо.
Вот ссылки обоих Джошуа Блоха (ранее работавшего в Sun в ядре Java, теперь работающего на Google)
[Эффективное]
Эффективная Java. Определенно лучшая Java-книга, которую не начинающий должен изучать, понимать и практиковать. Должно быть.
Эффективная Java
[Хороший API] Презентация, в которой рассказывается о дизайне API, возможности его повторного использования и смежных темах.
Это немного долго, но это стоит каждую минуту.
Как разработать хороший API и почему это важно
С уважением.
Обновление: взгляните на минуту 42 видео ссылки, которую я вам отправил. Об этом говорит эта тема:
"Если у вас есть два класса в публичном API и вы думаете, что один из них должен быть подклассом другого, как, например, Foo является подклассом Bar, спросите себя, является ли Every Foo Bar? ..."
И в предыдущей минуте говорится о «повторном использовании кода» во время разговора о TimeTask.