2011-11-23 16 views
40

Observo que en Java Reflection API hay dos métodos diferentes para invocar constructores: el método getDeclaredConstructors/getConstructors. Aunque los documentos de Java son ligeramente diferentes (getDeclaredConstructors parece implicar que devuelve TODOS los constructores, en lugar de los públicos), no está claro por qué la API admite explícitamente estos dos métodos diferentes.¿Cuál es la diferencia entre getDeclaredConstructors y getConstructors en Class API?

Más importante aún, me pregunto: ¿cuándo un método preferible a otra si estamos invocando clases dinámicamente? Por ejemplo, ¿cuál es el propósito de acceder a un constructor privado?

Respuesta

46

getDeclaredConstructors (cuando se quiere todo los constructores)

Devuelve una matriz de objetos que reflejan Constructor todos los constructores declarados por la clase que representa este objeto Class. Estos son públicos, protegidos, acceso predeterminado (paquete) y constructores privados.

getConstructors (cuando se quiere sólo public constructores)

Devuelve una matriz que contiene los objetos de constructor que reflejan todos los constructores públicos de la clase que representa este objeto Class.

Así, mirando la referencia para los dos, creo que la diferencia es que getConstructors devuelve sólo public constructores, mientras que getDeclaredConstructors devuelve todos los constructores (public, protected, acceso por defecto (el paquete), y private)

Por lo tanto, es fácil si solo necesita los constructores public y luego usa getConstructors. De lo contrario, si necesita todos los constructores (sin tener en cuenta el modificador de acceso del constructor), utilice getDeclaredConstructors.

+7

y mediante el uso de constructor.setAccessible (true), puede llamar de forma reflexiva a los constructores que son privados. – MeBigFatGuy

+0

Si bien esta respuesta es correcta, hay una pequeña advertencia. El compilador proporciona automáticamente un constructor público predeterminado (sin argumento) para cualquier clase que no defina explícitamente ningún constructor. 'getConstructors' no devolverá este constructor predeterminado, pero' getDeclaredConstructors' sí. – neXus

3

El método 'getDeclaredConstructors' devuelve solo los constructores que están declarados dentro de la clase. El método 'getConstructors' también devuelve constructores que no están declarados dentro de la clase pero que se heredan de las súper clases.

Así que depende de lo que va a hacer. No hay un enfoque correcto, realmente depende si también necesitas super constructores. Existen

+3

Esto está mal. Los métodos get * Constructors() no se comportan de manera similar a los métodos get * Methods(). Ambos buscan constructores de la clase determinada solamente, ignorando a los constructores de las superclases. (Su diferencia está en la visibilidad de los constructores que obtienen). Eso está de acuerdo con el hecho de que al crear una instancia de una clase debe usar uno de sus constructores, no puede omitirlos e invocar directamente uno de los constructores de su superclase. Puede escribir un par de clases de prueba para probar esto. (Lo hice). Elimine esta respuesta engañosa. –

+3

Los constructores no se heredan en Java. –

3

Los getDeclaredXX() métodos para la manipulación de las clases de maneras que no necesariamente destinado por el fabricante de esas clases. Tenga en cuenta que existe un método getDeclaredMethod() que le permite invocar métodos privados, y el método getDeclaredField() que le permite obtener/establecer campos privados.

No estoy del todo seguro acerca de casos de uso "legítimos", pero estos son obviamente útiles para hacer ciertas cosas. Además, esta familia de métodos solo devuelve cosas específicamente declaradas en la clase, no cosas que existen en la clase debido a la superclase.

Acceder a un constructor privado podría ser útil por las mismas razones, supongo.

0

Uso getDeclaredConstructors para crear una fábrica de clases cuyo constructor sea privado para evitar que los "usuarios" de mi sistema puedan crear estas clases directamente sin utilizar la fábrica. Encuentro este método bastante útil.

Cuestiones relacionadas