2013-01-09 10 views
16

Possible Duplicate:
Java: Instanceof and Genericsdlaczego instanceof nie działa z Generic?

Próbuję napisać funkcję, która rzuca ogólną listę do listy określonego typu. Znajdź poniższy kod

public <T>List<T> castCollection(List srcList, Class<T> clas){ 
    List<T> list =new ArrayList<T>(); 
    for (Object obj : srcList) { 
     if(obj instanceof T){ 
      ... 
     } 
    } 
    return list; 
} 

Ale obj instanceof T pokazując błąd kompilacji -

Cannot perform instanceof check against type parameter T. Use instead its erasure Object >instead since further generic type information will be erased at runtime.

żadnych wyjaśnień lub sposób, aby uzyskać pożądany rezultat?

Z góry dziękuję. :)

+1

.. ponieważ nie wyszukasz (-1); spróbuj '[java] ogólny instanceof' http://stackoverflow.com/questions/1570073/java-instanceof-and-generics, http://stackoverflow.com/questions/13768049/use-instanceof-in-a-eneric- way, http://stackoverflow.com/questions/8741984/why-t-instanceof-t-is-not-allowed-where-t-is-a-type-parametr-and-t-is-a-varia? lq = 1, http://stackoverflow.com/questions/4397660/generics-and-instanceof-java?rq=1 (etc) –

Odpowiedz

33

Nie możesz tego zrobić w ten sposób. Na szczęście masz już Class<T> argumentem więc zamiast zrobić

myClass.isAssignableFrom(obj.getClass()) 

ta zwróci true jeśli obj jest klasy myClass lub podklasy.

Jak @ILMTitan wskazał (dziękuje), musisz sprawdzić na obj == null, aby uniknąć potencjalnego wyjątku NullPointerException, lub użyj zamiast niego myClass.isInstance(obj). Albo robi to, czego potrzebujesz.

+5

To może spowodować, że zerowy wskaźnik obj to 'null'. 'isInstance()' nie spowoduje problemu z pustym wskaźnikiem. – ILMTitan

2

Po kompilacji generowane będą erased (generyczne są dla bezpieczeństwa typu kompilacji czasu) i zostaną zastąpione najbardziej stosownym typem po kompilacji.

Jeśli chcesz dokonać tej kompilacji zastąpić T z betonu typu przykładem

obj instance String 
4

T jest rodzajem parametryzowane i istnieje dla celów kompilacji. Nie istnieje w środowisku wykonawczym z powodu usunięcia typu.

Dlatego obj instanceof T nie jest legalne.

4

Ponieważ java używa usuwania, typy ogólne nie mogą być używane do sprawdzania. Aby uzyskać pożądany wynik, użyj Class.isInstance().

7

Krótka odpowiedź: ponieważ parametr typu w Javie jest czymś, co kompilator użył do nadania typu bezpieczeństwa.

W czasie wykonywania wpisz informacje o typach ogólnych jest odrzucana z powodu typu wymazania, ale instanceof jest sprawdzaniem w czasie wykonywania, które wymaga konkretnego typu (a nie zmiennej) do działania.

+0

Czy istnieje "instanceof' analogowy do sprawdzania podczas kompilacji? W moim przypadku, próbuję rzucić 'ClassCastException' jako część mojej definicji' add' metody 'Queue'. Moją pierwszą myślą było 'instanceof', ale podczas kompilacji dostałem' error: illegal genic typeof instanceof'. – Ungeheuer

+0

@Ungeheuer Powinieneś związać zmienną typu. – Jack