注解和反射以及通过注解反射实现getBean()方法

本文详细介绍了Java中的反射机制,包括Class、Package、Field、Method、Constructor以及Annotation的使用。同时,讲解了注解的定义、放置位置、作用以及常用的内置注解。通过注解反射,模拟实现了一个简单的Spring中getBean()方法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1.反射(reflect)

反射机制可以认为是用来描述一组类

1.1Class

用来描述类本身

如何获取Class

​ 如下三种方式

​ Class clazz = Class.forName(“包名.类名”);

​ Class clazz = 类名.class;

​ Class clazz = 对象.getClass();//Object类中的方法

Class中常用的方法

int modifiers = clazz.getModifiers(); 获取类修饰符,用整数对应,有两个修饰符则求和0->默认不写,1->public,2->private,4->protected,8->static,16->final,32->synchronized,64->volatile,128->transient,256->native,512->interface,1024->abstract

String name = clazz.getName();//获取类全名

String simpleName = clazz.getSimpleName();//获取类简单名字

Class sclazz = clazz.getSuperclass();//父类Class
System.out.println(sclazz.getName());//获取父类名字

Class[] classer = clazz.getInterfaces();//获取实现的接口

Person p = (Person) clazz.newInstance();//调用Person中默认无参数构造方法创建对象

1.2Package

//获取包名
Package p = clazz.getPackage();
p.getName();

1.3Field

用来描述类中的属性

int a = nameField.getModifiers();//获取属性的修饰符

Field nameField= clazz.getField(“name”);//获取类中的属性

Field[] fs= clazz.getFields();//获取所有属性,这两只能获取共有,包括继承过来的

Class fclass = nameField.getType();//获取属性类型

String fname = nameField.getName();//获取属性名

nameField.set(赋值的对象,“值”);//给属性赋值

nameField.get(对象名);//取值

//查看并修改私有属性

Field f = clazz.getDeclaredField(“属性名”);

Field[] fs = clazz.getDeclaredFields();//这两个只能获取当前类,不能获取父类

f.setAccessible(true);

f.get(对象);

f.set(对象,“值”);

1.4Method

用来描述类中的方法

Method method = clazz.getMethod(“方法名”,参数类型.class);//获取类中Method对象(只能得到共有的方法,包括自己的+父类继承过来的)

clazz.getMethods();//获取所有方法

method.getName();//获取方法名字,返回值String
method.getModifiers();//获取修饰符,返回值int
method.getReturnType();//获取方法类型,返回值为Class

method.getParameterTypes();//获取参数列表类型,返回值Class[]

method.getExceptionTypes();//获取抛出异常类型,返回值Class[]

method.invoke(对象名,“参数”);//执行方法

Method method = clazz.getDeclaredMethod(“方法名”,参数类型.class);//获取自己累公有+私有方法
method.setAccessible(true);//设置权限,为true才能用invoke方法执行它

1.5Constructor

用来描述类中的构造方法

Constructor con = clazz.getConstructor(参数类型.class);//获取构造方法
Person p = (Person) con.newInstance(“参数”);//调用构造方法创建对象

clazz.getConstructors();
clazz.getDeclaredConstructor();
clazz.getDeclaredConstructors();

con.setAccessible(true);

con.getModifiers();
con.getName();
con.getExceptionTypes();
con.getParameterTypes();

1.6Annotation

用来描述类中的注解@Override

2.注解

2.1注解的写法

​ @XXX[(一些信息)]

2.2注解放在那里

​ 类上面 属性上面 方法上面 构造方法上面 参数前面

2.3注解的作用

1.用来充当注释的作用

2.用来做代码的检测(验证)

3.可以携带一些信息

2.4Java中有一些人家写好的注解供我们使用

@Deprecated 用来说明方法是废弃的

@Override 用来做代码检测 检测是否重写

@SuppressWarnings(信息) String[] {"",""} 如果只有一个,省略大括号

​ unused 变量定义后未使用

​ serial 类实现了序列化接口,不添加序列ID号

​ raytypes 集合没有定义泛型

​ deprecation 方法已废弃

​ unchecked 出现了泛型的问题,可以不检测

​ all 包含以上所有,不推荐使用

2.5注解中可以携带信息 也可以不携带

信息不能随便写 信息的类型只能是如下的类型

​ 1.基本数据类型

​ 2.String类型

​ 3.枚举类型enum

​ 4.注解类型@

​ 5.数组类型[] 数组内部需要是如上的四种类型

2.6如何自己描述一个注解类型

1.通过@interface定义一个新的注解类型

2.发现写法与接口非常相似(可以利用接口的特点来记忆注解)

​ 可以描述 public static final的属性

​ 可以描述public abstract 的方法 方法要求返回值必须有 返回值的类型是如上那些

3.我们定义的注解如果要拿来使用,光定义还不够,还需要做很多细致的说明(需要利用Java提供好的注解来说明)

​ 元注解(也是注解,不是拿来使用的,是用来说明注解)

​ @Target 描述当前的这个注解可以放在那里写

​ @Retention 描述当前的这个注解存在什么作用域中的

​ 源代码文件–>编译–>字节码文件–>加载–>内存执行

​ SOURCE CLASS RUNTIME

​ @Inherited 描述当前这个注解是否能被子类对象继承

​ @Documented 描述当前这个注解能否被文档所记录

4.自己使用自己描述的注解

java

package testannotation;
imp
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值