ConstructiCat Logo
CodeBust.
Browse section ▾

Извлечение подкласса.

Problem

Класс имеет фичи, которые используются только в определённых случаях.

Solution

Создайте подкласс и используйте его в этих случаях.

##Example

До
Extract Subclass - Before
После
Extract Subclass - After

##Why Refactor

В основном классе находятся методы и поля для реализации какого-то редкого случая использования класса. Этот случай, хоть и очень редкий, является частью обязанностей класса, поэтому все связанные с ним поля и методы неправильно было бы вынести в абсолютно другой класс. Но, с другой стороны, их можно вынести в подкласс с помощью этого рефакторинга.

##Benefits

  • Создать подкласс довольно легко и быстро.

  • Можно выделить несколько разных подклассов, если основной класс реализует несколько подобных особых случаев.

##How to Refactor

  1. Создайте новый подкласс из интересующего вас класса.

  2. Если для создания объектов из подкласса будут нужны какие-то дополнительные данные, создайте конструктор и дополните его нужными параметрами. Не забудьте вызвать родительскую реализацию конструктора.

  3. Найдите все вызовы конструктора родительского класса. В тех случаях, когда требуется функциональность подкласса, замените родительский конструктор конструктором подкласса.

  4. Переместите нужные методы и поля из родительского класса в подкласс. Используйте для этого спуск метода и спуск поля. Проще всего начинать перенос с методов. Так поля будут доступны для них все время: из родительского класса до переноса, и из самого подкласса после окончания переноса.

  5. После того как подкласс готов, найдите все старые поля, которые управляли тем, какой набор функций должен выполняться. Эти поля можно удалить, заменив полиморфизмом все условные операторы, в которых они использовались. Простой пример — у вас в классе Автомобиль было поле isElectricCar, и в зависимости от него, в методе refuel() в машину либо заливается бензин, либо заряжается электричество. В результате рефакторинга, поле isElectricCar будет удалено, а классы Автомобиль и ЭлектроАвтомобиль будут иметь свои реализации метода refuel().