Путаница по поводу объявления объекта
Я изучаю Коллекции в книге CoreJava, и я нашел этот код:
List<String> a = new LinkedList<String>();
Теперь мне интересно, почему этот код не такой:
LinkedList<String> a = new LinkedList<String>();
Почему мы объявляем как список?
5 ответов
Код:
List<String> list = new LinkedList<String>();
лучше, чем:
LinkedList<String> list = new LinkedList<String>();
Это потому, что если вы объявили list
как List
и вы обнаружили, что производительность программы не очень хорошая, вы можете изменить код на:
List<String> list = new ArrayList<String>();
и посмотрите, работает ли программа быстрее. Прелесть этого в том, что вы можете внести это изменение без необходимости изменения остальной части кода.
В качестве вывода, если возможно, объявите ссылку в качестве интерфейса (List
это интерфейс):
List<String> list;
и вы можете легко переключить реализацию (class ArrayList
а также class LinkedList
являются реализациями интерфейса List
):
list = new LinkedList<String>();
или же
list = new ArrayList<String>();
Ваш второй будет работать и может быть предпочтительнее, если вам нужно использовать операции, специфичные для LinkedList
, Но такая необходимость обычно довольно редка. Первый является более общим - он позволяет использовать другой List
реализация путем изменения только одной строки. Другой код (например, параметры метода) не нужно менять.
PS Просто чтобы быть ясно - LinkedList
это конкретная реализация List
,
Список - это интерфейс, LinkedList - это конкретная реализация интерфейса. "Запрограммируйте на" интерфейс ", а не на" реализацию ": http://en.wikipedia.org/wiki/Design_Patterns
Еще один хороший пример.
Почему мы объявляем как список?
Рассмотрим метод:
public void doStuff(LinkedList llObj){}
Это показывает ограничение на метод, который пользователи разрешают только передавать LinkedList.
public void doStuff(List listObj) {}
в то время как этот метод позволяет передавать любой список.
надеюсь это поможет.
В Java, как и во всех других языках ООП, одним из основных преимуществ проектирования является полиморфизм. Полиморфизм просто не включает методы, но распространяется и на классы и принимает имена, такие как подтипы, политипизм и т. Д.
В вашем первом примере кода:
List<String> a = new LinkedList<String>();
Заставляет тип ссылочной переменной 'a' принимать любые конкретные расширения типа 'List'.
Где, как в следующем примере кода:
LinkedList<String> a = new LinkedList<String>();
Ссылочная переменная 'a' может принимать любые расширения типа 'LinkedList'.
Чтобы понять всю силу этого, мы должны проверить иерархию типов LinkedList: http://docs.oracle.com/javase/7/docs/api/java/util/LinkedList.html
Таким образом, в первом примере вы увеличиваете область ссылки "a" на любой конкретный тип "List", который также включает LinkedList, где, как и во втором примере, вы уменьшаете свою область действия до типа "LikedList" и его подтипов.
Один не лучше другого, но многое зависит от вашего дизайна кода и приложения в отношении того, какой подход лучше всего подходит для вашего варианта использования.
Некоторые хорошие чтения:
Полиморфизм подтипов: http://en.wikipedia.org/wiki/Polymorphism_(computer_science)