English | 简体中文 | 繁體中文 | Русский язык | Français | Español | Português | Deutsch | 日本語 | 한국어 | Italiano | بالعربية

Explicación detallada de la reflexión en Java

Índice de lectura

  1. API de reflexión de Java
  2. Crear instancias de objetos mediante reflexión
  3. Llamar a métodos privados a través de la reflexión
  4. Acerca del herramienta javap
  5. Referencias

API de reflexión de Java

Reflexión de JavaSe refiere al proceso de obtener las propiedades y métodos de una clase o modificar el comportamiento en tiempo de ejecución de la clase en estado de ejecución.

Clase java.lang.ClassOfrece muchos métodos para obtener metadatos, verificar y cambiar el comportamiento en tiempo de ejecución de las clases.

La reflexión en Java se refiere principalmente a las clases bajo java.lang y java.lang.reflect.

Ejemplos de aplicaciones de reflexión

  1. IDE, como Eclipse, MyEclipse, NetBeans, etc.
  2. Depuradores;
  3. Herramientas de prueba, etc.
  4. Various frameworks, como spring, hibernate, etc.

Clase java.lang.Class

La clase java.lang.Class proporciona las siguientes dos funciones principales:

  1. Proporciona métodos para acceder a los metadatos de la clase durante la ejecución;
  2. Proporciona métodos para verificar y modificar el comportamiento de la clase en tiempo de ejecución;

Métodos comunes de la clase java.lang.Class

Método Descripción
1) public String getName() Devuelve el nombre de la clase
2) public static Class forName(String className)throws ClassNotFoundException Carga la clase y devuelve el objeto Class
3) public Object newInstance()throws InstantiationException,IllegalAccessException Crea un objeto de instancia
4) public boolean isInterface() Determina si es una interfaz
5) public boolean isArray() Determina si es un array
6) public boolean isPrimitive() Determina si es un tipo de datos primitivo
7) public Class getSuperclass() Devuelve la referencia de Class del padre
8) public Field[] getDeclaredFields()throws SecurityException Devuelve el array de campos de propiedad de la clase
9) public Method[] getDeclaredMethods()throws SecurityException Devuelve el array de métodos de la clase
10) public Constructor[] getDeclaredConstructors()throws SecurityException Devuelve el array de métodos de la clase
11) public Method getDeclaredMethod(String name,Class[] parameterTypes)throws NoSuchMethodException,SecurityException Devuelve el método especificado del tipo de parámetro de la clase

¿Cómo obtener el objeto Class?

Hay tres formas, como se muestra a continuación:

  1. El método forName() de la clase Class, carga dinámica, en tiempo de ejecución, comienza a cargar la clase y realiza la inicialización estática de la clase
  2. Método getClass() del objeto, carga estática (cargada en tiempo de compilación)
  3. Sintaxis .class, carga estática (cargada en tiempo de compilación)

Ejemplo de método forName():

Se puede usar para cargar dinámicamente, cuando se conoce el nombre completo de la clase. Tenga en cuenta que los tipos de datos primitivos no se aplican a este método;

package tmp;
class Simple
{
}
public class Test
{
 public static void main(String args[]) throws ClassNotFoundException
 {
 try63Class<&#
 System.out.println(c.getName());
 System.out.println(c.getSimpleName());
 }
}
tmp.Simple
Simple

Ejemplo de método getClass():

Obtener el objeto Class desde el objeto de instancia

package tmp;
class Simple
{
}
public class Test
{
 void printName(Object obj)
 {
 }
 public static void main(String args[])
 {
 Simple s = new Simple();
 try63; extends Object> c = s.getClass();
 System.out.println(c.getName());
 System.out.println(c.getSimpleName());
 }
}
tmp.Simple
Simple

Ejemplo de sintaxis .class

Actúa sobre el nombre de la clase, también se puede aplicar a tipos de datos primitivos, como se muestra a continuación:

package tmp;
public class Test
{
 public static void main(String args[])
 {
 Class<Boolean> c = boolean.class;
 System.out.println(c.getName());
 Class<Test> c2 = Test.class;
 System.out.println(c2.getName());
 }
}
boolean
tmp.Test

Determinar el tipo de objeto Class

Los siguientes métodos se pueden usar para determinar el tipo de objeto Class:

1) public boolean isInterface(): ¿Corresponde a una interfaz?
2) public boolean isArray(): ¿Corresponde a un array?
3) public boolean isPrimitive(): ¿Corresponde al tipo de datos primitivo?

Ejemplo de código:

package tmp;
class Simple
{
}
interface My
{
}
public class Test
{
 public static void main(String args[])
 {
 this.msg = s;
 {
 try63Class<&#
 System.out.println(c.isInterface());
 try63;> c2 = Class.forName("tmp.My");
 System.out.println(c2.isInterface());
 }
 catch (Exception e)
 {
 System.out.println(e);
 }
 }
}
false
true

Crear instancias de objetos mediante reflexión

Hay dos formas, como se muestra a continuación:

  1. Creado mediante el método newInstance() del objeto Class, este método solo puede invocar el constructor sin parámetros;
  2. Creado mediante el método newInstance() del objeto Constructor, este método es adecuado para métodos de constructor con parámetros y también puede romper el patrón de singleton, invocar métodos de constructor privados;

所以,通常来讲,第二种方式比第一种使用范围更广。

Por lo tanto, en términos generales, la segunda manera es más amplia en términos de uso que la primera.

package tmp;
class Simple
{
 private String msg;
 {
 Ejemplo de llamada al método newInstance() del objeto Class
 }
}
public class Test
{
 public static void main(String args[])
 {
 this.msg = s;
 {
 try63Class<&#
 System.out.println("Hello Java");
 s.message();
 }
 catch (Exception e)
 {
 System.out.println(e);
 }
 }
}

Simple s = (Simple) c.newInstance();

Hello Java

Ejemplo de llamada al método newInstance() del objeto Constructor

package tmp;
Nota: aquí se puede obtener el constructor específico según el tipo de parámetro传入, y también se puede cambiar la restricción de acceso al constructor.
class Simple
{
 import java.lang.reflect.Constructor;
 private String msg;
 {
 void message() + System.out.println("Hello Java,"
 }
 msg);
 private Simple(String s){
 }
}
public class Test
{
 public static void main(String args[])
 {
 this.msg = s;
 {
 try63Class<&#
 ;> c = Class.forName("tmp.Simple");63;> con = c.getDeclaredConstructor(String.class);
 con.setAccessible(true);
 Simple s = (Simple) con.newInstance("...");
 s.message();
 }
 catch (Exception e)
 {
 System.out.println(e);
 }
 }
}

Hello Java,...

Llamar a métodos privados a través de la reflexión

A través de la reflexión, podemos llamar a métodos privados de otras clases, principalmente involucra las clases java.lang.Class y java.lang.reflect.Method;

Principalmente se utiliza el método setAccessible de la clase Method y el método invoke, el primero modifica los permisos de acceso, y el segundo llama al método.

A través de la invocación de un ejemplo de método privado con parámetros:

package tmp;
import java.lang.reflect.Method;
class A
{
 private void cube(int n)
 {
 System.out.println(n * n * n);
 }
}
class Test
{
 public static void main(String args[]) throws Exception
 {
 Class<A> c = A.class;
 Object obj = c.newInstance();
 Method m = c.getDeclaredMethod("cube", new Class[]{ int.class });
 m.setAccessible(true);
 m.invoke(obj, 4);
 }
}

Acerca del herramienta javap

El comando javap puede desensamblar archivos de bytecode de java, mostrar información de campos, métodos de construcción y métodos comunes en archivos de clase;

Instrucciones de uso:

Ejemplo de javap java.lang.Object

javap -Ejemplo de c Test:

Escribir una clase Test simple, como se muestra a continuación:

package tmp;
class Simple
{
}
public class Test
{
 public static void main(String args[])
 {
 System.out.println("Hello");
 }
}

Escribir javap -c Test:

Referencias

Prácticamente es una traducción, se han realizado algunas modificaciones menores

http://www.javatpoint.com/java-reflexión

Esto es todo el contenido de este artículo, espero que el contenido de este artículo pueda proporcionar cierta ayuda a su aprendizaje o trabajo, y también espero que apoyen más al tutorial de grito!

Declaración: Este artículo se ha obtenido de la red, es propiedad del autor original, el contenido ha sido subido por usuarios de Internet de manera autónoma, este sitio web no posee los derechos de propiedad, no ha sido editado por humanos y no asume responsabilidades legales relacionadas. Si encuentra contenido sospechoso de infracción de derechos de autor, por favor envíe un correo electrónico a: notice#w proporcionando evidencia relevante, una vez confirmado, este sitio eliminará inmediatamente el contenido sospechoso de infracción.3Declaración: El contenido de este artículo se ha obtenido de la red, es propiedad del autor original, el contenido ha sido subido por usuarios de Internet de manera autónoma, este sitio web no posee los derechos de propiedad, no ha sido editado por humanos y no asume responsabilidades legales relacionadas. Si encuentra contenido sospechoso de infracción de derechos de autor, por favor envíe un correo electrónico a: notice#w proporcionando evidencia relevante, una vez confirmado, este sitio eliminará inmediatamente el contenido sospechoso de infracción.

Te gustará