Gibt es einen Präferenz- oder Verhaltensunterschied zwischen der Verwendung von:
if(obj.getClass().isArray()) {}
und
if(obj instanceof Object[]) {}
?
Gibt es einen Präferenz- oder Verhaltensunterschied zwischen der Verwendung von:
if(obj.getClass().isArray()) {}
und
if(obj instanceof Object[]) {}
?
Erickson
In den meisten Fällen sollten Sie die verwenden instanceof
-Operator, um zu testen, ob ein Objekt ein Array ist.
Im Allgemeinen testen Sie den Typ eines Objekts, bevor Sie ihn auf einen bestimmten Typ umwandeln, der zur Kompilierzeit bekannt ist. Vielleicht haben Sie zum Beispiel Code geschrieben, der mit a arbeiten kann Integer[]
oder ein int[]
. Sie möchten Ihre Abgüsse mit schützen instanceof
:
if (obj instanceof Integer[]) {
Integer[] array = (Integer[]) obj;
/* Use the boxed array */
} else if (obj instanceof int[]) {
int[] array = (int[]) obj;
/* Use the primitive array */
} else ...
Auf der JVM-Ebene ist die instanceof
Operator übersetzt in ein bestimmtes “Instanz von” Byte-Code, der in den meisten JVM-Implementierungen optimiert ist.
In selteneren Fällen verwenden Sie möglicherweise Reflektion, um einen Objektgraphen unbekannten Typs zu durchlaufen. In solchen Fällen ist die isArray()
-Methode kann hilfreich sein, da Sie den Komponententyp zur Kompilierzeit nicht kennen; Sie könnten beispielsweise eine Art Serialisierungsmechanismus implementieren und in der Lage sein, jede Komponente des Arrays unabhängig vom Typ an dieselbe Serialisierungsmethode zu übergeben.
Es gibt zwei Sonderfälle: Nullreferenzen und Referenzen auf primitive Arrays.
Eine Nullreferenz wird verursachen instanceof
resultieren false
während isArray
wirft ein NullPointerException
.
Angewendet auf ein primitives Array, the instanceof
Erträge false
es sei denn, der Komponententyp auf dem rechten Operanden stimmt genau mit dem Komponententyp überein. Im Gegensatz, isArray()
wird zurückkehren true
für jeden Bauteiltyp.
Ja, aber wie viel Unterschied wird es machen? Das klingt für mich nach Mikrooptimierung.
– Michael myers
♦
20. Oktober 2008 um 21:26 Uhr
@Dims Wenn Sie das behaupten obj instanceof int[]
Erträge false
wenn Sie eine zuweisen int[]
zu obj
du liegst falsch.
– Ericsson
13. Februar 2013 um 16:58 Uhr
Entschuldigung, das meinte ich obj instanceof Object[]
Erträge false
wenn Object obj = new int[7]
.
– Dimmt
13. Februar 2013 um 17:07 Uhr
Richtig, in Java sind primitive Datentypen keine Objekte und werden nicht erweitert java.lang.Object
, das macht also Sinn. Aber instanceof
kann weiterhin zum Testen auf primitive Arrays verwendet werden.
– Ericsson
13. Februar 2013 um 17:26 Uhr
-1: Allgemein, da primitive Arrays sind Arrays aufrufen isArray()
sollte benutzt werden. In der sehr nicht allgemein Sonderfall, nur Arrays von Objekten zu haben, instanceof
bietet eine leistungsstarke Alternative.
– Sam Harwell
23. April 2013 um 13:34 Uhr
Burkhard
Im letzteren Fall, wenn obj null ist, erhalten Sie keine NullPointerException, sondern ein false.
Wenn obj
ist vom Typ int[]
sagen, dann wird das ein Array haben Class
aber keine Instanz von sein Object[]
. Also was willst du damit machen obj
. Wenn Sie es werfen wollen, machen Sie mit instanceof
. Wenn Sie Reflektion verwenden wollen, dann verwenden Sie .getClass().isArray()
.
Sebastien Tardif
getClass().isArray()
ist unter Sun Java 5 oder 6 JRE deutlich langsamer als unter IBM.
So viel, dass mit clazz.getName().charAt(0) == '['
is faster on Sun JVM.
dturanski
I recently ran into an issue upgrading a Groovy application from JDK 5 to JDK 6. Using isArray()
failed in JDK6:
MissingMethodException:
No signature of sun.reflect.generics.reflectiveObjects.GenericArrayTypeImpl.isArray() ...
Changing to instanceof Object[]
das behoben.
Das macht keinen Sinn. isArray
ist eine Methode der Class
nicht Type
also natürlich GenericArrayTypeImpl
hat diese Methode nicht. Und getClass
kann niemals eine Nicht-Class
Type
also müssen Sie (oder Groovy??) etwas falsch gemacht haben, um dies zu bekommen, wie zum Beispiel die Annahme von every Type
ist ein Class
.
– kaqqao
8. Dezember 2017 um 13:06 Uhr
Bill K
Wenn Sie jemals die Wahl zwischen einer reflektierenden und einer nicht reflektierenden Lösung haben, wählen Sie niemals die reflektierende Lösung (mit Klassenobjekten). Es ist nicht so, dass es „falsch“ oder so wäre, aber alles, was mit Reflexion zu tun hat, ist im Allgemeinen weniger offensichtlich und weniger klar.
Das macht keinen Sinn. isArray
ist eine Methode der Class
nicht Type
also natürlich GenericArrayTypeImpl
hat diese Methode nicht. Und getClass
kann niemals eine Nicht-Class
Type
also müssen Sie (oder Groovy??) etwas falsch gemacht haben, um dies zu bekommen, wie zum Beispiel die Annahme von every Type
ist ein Class
.
– kaqqao
8. Dezember 2017 um 13:06 Uhr
Trenton D. Adams
Die Java-Array-Reflektion ist für Fälle gedacht, in denen Sie keine Instanz der Klasse zur Verfügung haben, um “instanceof” auszuführen. Wenn Sie beispielsweise eine Art Injection-Framework schreiben, das Werte in eine neue Instanz einer Klasse einfügt, wie es JPA tut, müssen Sie die isArray()-Funktionalität verwenden.
Ich habe Anfang Dezember darüber gebloggt.
http://blog.adamsbros.org/2010/12/08/java-array-reflection/