JDK 之 Java Bean 内省机制
JDK 之 Java Bean 内省机制
JDK 规范目录(https://www.cnblogs.com/binarylei/p/10200503.html)
JavaBean 是一种特殊的 Java 类,主要用于传递数据信息,这种 Java 类中的方法主要用于访问私有的字段,且方法名符合某种命名规则。
一、JavaBean
1.1 JavaBean 命名规则
一个 JavaBean 类中的方法,去掉 set 或 get 前缀,剩余部分就是属性名,如果剩余部分的第二个字母是小写的,则把剩余部分的首字母改成小的。
getAge/setAge --> age
gettime --> time
setTime --> time如果去掉前缀,剩余部分的第二个字母为大写,则全部大写
getCPU --> getCPU
1.2 什么叫做内省?
Java 内省主要使用来对 JavaBean 进行操作的,所以当一个类满足了 JavaBean 的条件,就可以使用内省的方式来获取和操作 JavaBean 中的字段值。内省提供了操作 JavaBean 的 API。
Java 中提供了一套 API 用来访问某个属性的 getter/setter 方法,通过这些 API 可以使你不需要了解这个规则,这些 API 存放于包 java.beans 中,一般的做法是通过类 Introspector 的 getBeanInfo 方法 来获取某个对象的 BeanInfo 信息,然后通过 BeanInfo 来获取属性的描述器(PropertyDescriptor),通过这个属性描述器就可以获取某个属性对应的 getter/setter 方法,然后我们就可以通过反射机制来调用这些方法。
二、JDK 内省机制
2.1 Introspector 类
Introspector 这个类位于 java.beans 包中,该类中的方法都是静态的,可以直接使用类名调用。
// 获取 beanClass 及其所有父类的 BeanInfo
BeanInfo getBeanInfo(Class<?>beanClass)
// 获取 beanClass 及其指定到父类 stopClass 的 BeanInfo
BeanInfo getBeanInfo(Class<?> beanClass, Class<?> stopClass)
我们可以使用 Introspector 的 getBeanInfo(Class<?> beanClass) 来获取一个 JavaBean 类的 BeanInfo 对象。BeanInfo 有三个常用的属性:
// bean 信息
BeanDescriptor beanDescriptor = beanInfo.getBeanDescriptor();
// 属性信息
PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors();
// 方法信息
MethodDescriptor[] methodDescriptors = beanInfo.getMethodDescriptors();
2.2 PropertyDescriptor 类
这个类位于 java.beans 包中。
@Test
public void test() throws Exception {
PropertyDescriptor pd = new PropertyDescriptor("id", User.class);
System.out.println(pd.getName());
}
2.3 PropertyEditor 类
Spring 中使用 PropertyEditor 向 JavaBean 中注入属性。
@Test
public void test1() throws Exception {
User user = new User();
PropertyDescriptor propertyDescriptor = new new PropertyDescriptor("id", User.class);
propertyDescriptor.setPropertyEditorClass(IntPropertyEditor.class);
PropertyEditor propertyEditor = propertyDescriptor.createPropertyEditor(user);
propertyEditor.setAsText("99");
Method writeMethod = propertyDescriptor.getWriteMethod();
writeMethod.invoke(user, propertyEditor.getValue());
System.out.println(user);
}
@Test
public void test2() throws Exception {
User user = new User();
PropertyDescriptor propertyDescriptor = new new PropertyDescriptor("id", User.class);
propertyDescriptor.setPropertyEditorClass(IntPropertyEditor.class);
PropertyEditor propertyEditor = propertyDescriptor.createPropertyEditor(user);
// 这个 evt 实际上就是 propertyEditor 对象
propertyEditor.addPropertyChangeListener(evt -> {
PropertyEditor source = (PropertyEditor) evt.getSource();
Method writeMethod = propertyDescriptor.getWriteMethod();
writeMethod.invoke(user, source.getValue());
});
propertyEditor.setAsText("99");
System.out.println(user);
}
// JDK 中的 PropertyEditor 接口
public static class IntPropertyEditor extends PropertyEditorSupport {
@Override
public void setAsText(String text) throws IllegalArgumentException {
setValue(Integer.parseInt(text));
}
}
三、Apache BeanUtils 工具包
Apache 组织开发了一套用于操作 JavaBean 的 API(内省)。该工具在 commons-beanutils 包中,核心类 BeanUtils:
setProperty(bean, name, value)
copyProperties(target, source)
可以支持 String 到 8 中基本数据类型转换,其他引用数据类型都需要注册转换器 ConvertUtils.register(Converter, Class)
使用 BeanUtils 来格式化日期:
public static void main(String[] args) throws Exception {
User user = new User();
String name = "zhangsan";
String birthday = "19801122";
// 注册一个转换器
/* 使用匿名内部类来注册转换器
ConvertUtils.register(new Converter() {
public Object convert(Class beanClass, Object value) {
String birthday = (String) value;
SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMdd");
try {
return sdf.parse(birthday);
} catch (ParseException e) {
return null;
}
}
}, Date.class);
*/
DateConverter converter = new DateConverter();
converter.setPatterns(new String[]{"yyyy-MM-dd","yyyyMMdd","MM/dd/yyyy"});
ConvertUtils.register(converter, Date.class);
BeanUtils.setProperty(user, "name", name);
BeanUtils.setProperty(user, "birthday", birthday);
System.out.println(user);
}
参考:
- 《JavaBean 以及内省技术详解》:https://www.cnblogs.com/yejiurui/archive/2012/10/06/2712693.html
每天用心记录一点点。内容也许不重要,但习惯很重要!
JDK 之 Java Bean 内省机制的更多相关文章
- Java的内省机制
我现在的理解就是,Java的内省机制就是针对JavaBean的,可以获取到类的属性名称,以及属性的Getter和Setter方法,应该是在写框架的时候才会用到内省机制,还有一个地方可以用到内省机制,就 ...
- java内省机制及PropertyUtils使用方法
背景 一般情况下,在Java中你可以通过get方法轻松获取beans中的属性值.但是,当你事先不知道beans的类型或者将要访问或修改的属性名时,该怎么办?Java语言中提供了一些像java.bean ...
- 【代码笔记】Java——远程监控、反射、代理、内省机制
远程控制的基本原理 远程控制(RemoteControl)拥有控制端和被控端双方. 控制方通过请求,取得对远端的操作,实现远端的事件回放功能,同时,应该看得到远端桌面的画面.而被控方必须在建立Serv ...
- java内省机制Introspector
访问JavaBean属性的两种方式 1)直接调用bean的setXXX或getXXX方法: 2)通过内省技术访问(java.beans包提供了内省的API),内省技术访问也提供了两种方式: a)通过P ...
- Java内省机制
转自: https://blog.csdn.net/hahalzb/article/details/5972421 1.java内省机制其实通俗的理解为,对自身的进行一个扫描,这个扫描的对象就是我们普 ...
- Java动态代理机制详解(JDK 和CGLIB,Javassist,ASM)
class文件简介及加载 Java编译器编译好Java文件之后,产生.class 文件在磁盘中.这种class文件是二进制文件,内容是只有JVM虚拟机能够识别的机器码.JVM虚拟机读取字节码文件,取出 ...
- Java 动态代理机制详解(JDK 和CGLIB,Javassist,ASM)
class文件简介及加载 Java编译器编译好Java文件之后,产生.class 文件在磁盘中.这种class文件是二进制文件,内容是只有JVM虚拟机能够识别的机器码.JVM虚拟机读取字节码文件,取出 ...
- Java学习系列(一)Java的运行机制、JDK的安装配置及常用命令详解
俗话说:“十五的月亮十六圆”.那学习是不是也是如此呢?如果把月亮看成是我们的愿望,那十五便是我们所处的“高原期”,坚持迈过这个坎,我相信你的愿望终究会现实的.记得马云曾说:今天很残酷,明天更残酷,后天 ...
- java的运行机制及初步相关配置(jdk)
java的运行机制: 计算机高级语言的类型主要有编译型和解释型两种,而java语言是两种类型的结合. java首先利用文本编译器编写java源程序,源文件的后缀名为.java:再利用编译器(javac ...
随机推荐
- NCBI之gene系列
1.基因系列中的data索引 2.基因ID之间的转换 对于生信,依托于别人的工具不如自己动手,由于研究发表的滞后性,往往很多工具提供的转换并不是最新的,况且开发者水平也参差不齐,理解原理才能让你来去自 ...
- spring 代理注解 <aop:aspectj-autoproxy />
spring默认使用jdk的代理方式,使用jdk的代理方式我们知道,代理的类需要实现一个接口,若果没有就会报,java.lang.NoSuchMethodException: com.sun.prox ...
- Oracle 存储过程例子返回记录集
转载:https://www.cnblogs.com/mikalshao/articles/1454134.html Oracle 不支持批量查询,因此无法从一个命令返回多个结果集.使用存储过程时,返 ...
- powerdesigenr设置主外键颜色
使用PowerDesigner时,它默认table的字体大小颜色等非常难看: 如果通过 Symbol ---> Format进行设置,只能对选中的最修改,新建的Table无效. 可以通过如下修改 ...
- 8 种 NoSQL 数据库系统对比(转自: http://blog.jobbole.com/1344/)
导读:Kristóf Kovács 是一位软件架构师和咨询顾问,他最近发布了一片对比各种类型NoSQL数据库的文章. 虽然SQL数据库是非常有用的工具,但经历了15年的一支独秀之后垄断即将被打破.这只 ...
- Centos7 下的NTP-server(Chorny) 部署及客户端时间同步配置
一.介绍 1.本博客以 ceph 集群搭建时的NTP-server 为例. 2.hosts # vim /etc/hosts 10.6.32.20 ceph1 (作为时间服务器) 10. ...
- Linux下查看编辑二进制文件:hexedit神器
1.如果没有hexedit安装hexedit:2.打开终端输入hexedit filename;3.打开即可用键盘输入字符,用方向键移动,ctrl+w保存,ctrl+x退出:4.详细用法 man he ...
- Android 性能测试之内存 --- 追加腾讯性能案例,安卓抓取性能扫盲帖
内存测试: 思路 目前做的是酒店APP,另下载安装几个个第三方酒店的APP以方便对比(相当于可以做竞品测试) 数据的获取来源是ADB底层命令,而且最好是不需要root权限,因为很多手机root很麻烦或 ...
- SQL Server中row_number的用法
ROW_NUMBER()函数将针对SELECT语句返回的每一行,从1开始编号,赋予其连续的编号.在查询时应用了一个排序标准后,只有通过编号才能够保证其顺序是一致的,当使用ROW_NUMBER函数时,也 ...
- ECMAScript2017之async function
An async function can contain an await expression that pauses the execution of the async function an ...