深入理解J2SE—Introspector(内省)应用

上篇博客中主要介绍了Introspector的使用方法和概念,这篇博客中主要来写一些Introspector的应用。为什么要利用Introspector来对javabean进行get/set值,而不直接使用get/set方法。


例如。现在有一个User javabean。表单向后台服务器提交数据时,从表单中获取的数据会设置到User javabean中。然后利用User对象进行业务逻辑处理。

package com.ray.javaneisheng;

import java.util.Date;

public class User {
	private String name;
	private String password;
	
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public String getPassword() {
		return password;
	}
	public void setPassword(String password) {
		this.password = password;
	}
	@Override
	public String toString() {
		return "User [name=" + name + ", password=" + password + "]";
	}
	
}

1.一般情况下可以会利用request.getParameter()方法将数据设置到User对象中。此种方法比较繁琐,如果javabean对象中属性有多个,那每一个都要设置,这种方法显然是不够灵活,并且效率低。

	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		try {
			// User u = populate(User.class,request.getParameterMap());
			User u = new User();
			u.setName(request.getParameter("name"));
			u.setPassword(request.getParameter("password"));
			System.out.println(u);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}


2.上一篇文章中可以利用Introspector来操作和管理javabean的get/set方法。那这里我们也利用Introspector和request.getParameterMap()将表单中的数据,全部设置到user对象中。此种方法有有一个弊端只能支持String类型的变量。写的不够灵活,但是能体现出可以利用Introspector来灵活操作javabean的思想。

public class LoginServlet extends HttpServlet {

	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		try {
			 User u = populate(User.class,request.getParameterMap());
			System.out.println(u);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}

	/**
	 * 利用java内省来将parameterMap中的值放入到javabean对象中
	 */
	private User populate(Class<User> class1, Map<String, String[]> parameterMap)
			throws Exception, IllegalAccessException {
		// 创建出user对象
		User u = class1.newInstance();
		BeanInfo info = Introspector.getBeanInfo(u.getClass());
		PropertyDescriptor[] propertyDescriptors = info
				.getPropertyDescriptors();
		for (PropertyDescriptor propertyDescriptor : propertyDescriptors) {
			String[] params = parameterMap.get(propertyDescriptor.getName());
			if (params != null && params.length > 0) {
				propertyDescriptor.getWriteMethod().invoke(u, params[0]);
			}
		}
		return u;
	}



3.利用apache 提供了.commons-beanutils来将表单提交上来的内容设置到javabean中,这种方法同样是传入的参数ParameterMap。这种方法在封装的时候自动进行类型转化,但是只能在8个基本数据类型中转换。

public class LoginServlet extends HttpServlet {

	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		try {
			User u = new User();
			// BeanUtils 的 该方法还可以自动进行类型转换. 只能转换8中基本数据类型.
			BeanUtils.populate(u, request.getParameterMap());
			System.out.println(u);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
}
如果我们在 User javabean对象中加入了Date类型的属性,例如加入private Date birthday,并且提供get,set方法。这时在使用BeanUtils.populate方法时会抛出argument type mismatch异常。这种原因是BeanUtils.populate方法只支持8个基本数据类型中的转换。如果需要转换其他类型需要提供类型转化器,自定义转换规则。

public class MyConverter implements Converter {
 
	// 参数2 就是 将要被转换的String  ==>  1990-12-12
	// 参数1 提示你要把 参数2转换成什么类型的. ==>   Date
	public Object convert(Class arg0, Object obj) {
		SimpleDateFormat format =  new SimpleDateFormat("yyyy-MM-dd");
		try {
			return format.parse(obj.toString());
		} catch (Exception e) {
			throw new RuntimeException("类型转换失败");
		}
	}
 
}

并将该转换类注册

public class LoginServlet extends HttpServlet {

	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		try {
			User u = new User();
			// BeanUtils 的 该方法还可以自动进行类型转换. 只能转换8中基本数据类型.
			// 注册一个转换器, 来转换自定义类型
			ConvertUtils.register(new MyConverter(), Date.class);
			BeanUtils.populate(u, request.getParameterMap());
			System.out.println(u);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}}

以上就是内省的应用。这种方式很显然的更加方便的操作了javabean,尤其是提现在表单提交时间,后台服务器获取这些数据时。

我在猜测一件事就是BeanUtils.populate的源码是也是利用内省的机制实现的。下一步会想办法证实一下。





1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。、可私 6信博主看论文后选择购买源代码。 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 、可私信6博主看论文后选择购买源代码。 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 、可私信6博主看论文后选择购买源代码。
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值