Как поделиться кодом между некоторыми из подклассов? - PullRequest
2 голосов
/ 30 июня 2019

У меня есть абстрактный класс с несколькими подклассами (на данный момент их более 20), и есть код и переменные, которые я хотел бы разделить только между 2 подклассами.

Если я добавлю методы и переменные в суперкласс, тогда все подклассы будут иметь к ним доступ, но я хочу, чтобы только 2 подкласса имели к ним доступи в основном будет знать, что они существуют.Есть ли способ добиться этого?

Спасибо

Ответы [ 5 ]

5 голосов
/ 30 июня 2019

Вы можете решить эту проблему, применив композицию вместо наследования : создайте новый класс, содержащий функциональные возможности, которые должны совместно использоваться двумя подклассами, и используйте ссылку на экземпляр нового класса внутрииз 2 подклассов.

Таким образом, вы избежите необходимости иметь дополнительный слой между подклассами и суперклассом, и ваш код будет более гибким и простым в обслуживании.

Этот подходрекомендуется почти всегда, когда неестественно добавлять некоторые общие функции в суперкласс и получать их через наследование.Если вы сомневаетесь, всегда спрашивайте себя, является ли отношение HAS-A (композиция) более подходящим, чем отношение IS-A (наследование).

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

2 голосов
/ 30 июня 2019

Все проблемы в информатике могут быть решены с помощью другого уровня косвенности. ( Дэвид Уилер )

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

Приведенная выше цитата не всегда верна, но, по крайней мере, концептуально , еще одна полезная абстракция - чаще всего лучший выход из проблемы проектирования.

1 голос
/ 30 июня 2019

Помимо наследования вы можете использовать композицию. Создайте другой класс, поместите в него ваши методы и переменные и сделайте ссылку на этот новый класс в ваших 2 классах. Также, используя правильную упаковку и модификаторы доступа, вы можете получить доступ к вашему новому классу только из этих двух клиентских классов. Надеюсь, это поможет.

0 голосов
/ 30 июня 2019

Давайте создадим реальный пример, чтобы вы могли видеть, как решить эту проблему.

У нас есть класс с именем Alive. Мы будем использовать это как родительский класс Dog, Wolf и Human. Где нам нужно Dog и Wolf, чтобы иметь метод growl(), но Human нет.

class Alive{

    abstract void smell(){};
    abstract void see(){};
    abstract void hear(){};
 }

class Canis extends Alive{

    abstract void growl(){};
 }

class Human extends Alive{
}

class Dog extends Canis{
}

class Wolf extends Canis{
}

Это диаграмма того, как выглядит иерархия наследования:

                             Alive  
                             /  \
                            /    \
                           /      \
                        Human    Canis
                                  / \
                                 /   \
                               Dog   Wolf    
0 голосов
/ 30 июня 2019

Вы можете расширить абстрактный класс из базового класса, поместить методы, которые вы хотите использовать в этом классе, а затем расширить два класса, которые вы хотите использовать совместно, из нового класса промежуточного программного обеспечения.

...