Java instanceof реализует/расширяет

Как именно работает instanceof? Когда у меня есть иерархия объектов, которые расширяют и реализуют друг друга, работает ли экземпляр чего-либо через эти обе линии?

Например, я хочу знать, является ли мой объект экземпляром Listили ArrayList или Collection?

Я изучил это дерево, http://docs.oracle.com/javase/6/docs/api/java/util/package-tree.html

И, кажется, все они, конечно, подпадают под Object, но то, что мне нужно, я думаю, это AbstractCollection или даже обычный Collection, потому что это кажется самым высоким в иерархии.

Будет ли все в порядке, если я проверяю объект только по Collection, чтобы охватить все эти 3 класса?


person Jaanus    schedule 07.12.2012    source источник


Ответы (4)


Будет ли у меня все в порядке, когда я проверяю объект только по коллекции, чтобы охватить все эти 3 класса?

Да, instanceof Collection вернет true для всех реализаций (прямых или косвенных) интерфейса Collection.

В редком случае, когда вы этого не хотите, вам придется использовать отражение. Например, Class# getDeclaredClasses предоставит вам список всех классов и интерфейсов, которые напрямую расширяются/реализуются классом.

Как только вы узнаете, что что-то является коллекцией, вы можете привести это, чтобы получить доступ к его методам (например, iterator):

  if (myObject instanceof Collection){
      Collection<?> c = (Collection<?>) myObject;
      for (Object o: c){
         // do something with every element in the collection
      }
  }
person Thilo    schedule 07.12.2012
comment
хорошо, после получения значения true, могу ли я как-то получить первый элемент, есть ли у них общий метод, который я могу использовать, потому что, поскольку они instanceof Collection, я должен иметь возможность использовать iterator.next() - person Jaanus; 07.12.2012
comment
О, вы хотите перебрать все классы, реализующие Collection? Нет никакого реального способа сделать это. Для чего вам это нужно? - person Thilo; 07.12.2012
comment
Или вам нужно дерево классов и интерфейсов, от которых наследуется ваш класс X? Это вы можете сделать с помощью отражения: Class#getClasses docs.oracle.com/javase/1.5.0/docs/api/java/lang/ - person Thilo; 07.12.2012
comment
Сначала я хочу проверить, получаю ли я какой-то массив, например, как я сказал List , ArrayList и т. д. Если это правда, я хочу взять первый элемент и проверить, является ли он instanceof MyClass. Вот почему я хотел использовать итератор... чтобы получить первый элемент. Это возможно? - person Jaanus; 07.12.2012
comment
Хорошо, в этом случае вы бы сделали instanceof Collection, и если это так, то вы делаете приведение: Collection c = (Collection)theObject;, а затем вы можете сделать c.iterator() и работать с этим. - person Thilo; 07.12.2012
comment
О, хорошо, это то, что я сделал сам, мне просто интересно, все ли объекты Collection могут обрабатывать эту команду итератора. - person Jaanus; 07.12.2012
comment
Им лучше обрабатывать итераторы, потому что это необязательный метод интерфейса Collection. Это именно то, что дает вам строгая типизация Java: гарантии того, что определенные объекты имеют определенные методы. - person Thilo; 07.12.2012

if(obj instanceof Collection) 

Вернет true, если объект представляет собой какую-либо коллекцию. Таким образом, он вернет true для ваших 3 случаев, однако он также вернет true для других случаев, таких как HashMap.

person cowls    schedule 07.12.2012

Оператор instanceof вернет true, если проверяемый объект является классом или подклассом данного класса или если он (или один из его предков) реализует данный интерфейс.

person Averroes    schedule 07.12.2012

Будет ли у меня все в порядке, когда я проверяю объект только по коллекции, чтобы охватить все эти 3 класса?

Не всегда.

Возможно, что объект is-a есть Collection, но ArrayList.

Например:

ArrayList anArrList = new ArrayList();
HashMap ahashMap = new HashMap();

anArrList instanceof Collection // true
ahashMap instanceof Collection // true

но оба находятся в другой иерархии.

person Azodious    schedule 07.12.2012