Java通过DOM解析假装实现Spring中Bean注入
Posted GaoYang-笔迹
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java通过DOM解析假装实现Spring中Bean注入相关的知识,希望对你有一定的参考价值。
通过DOM解析假装实现Spring中Bean注入
一、案例需求
通过反射的形式去创建对象,只要通过传入xml配置,我们使用DOM解析xml的方式,去读取数据,根据数据去创建对象和简单属性赋值!该案例在于更好的理解Spring中的IOC容器
本文参考博文:XML解析之DOM解析详解
二、步骤结解析
- 创建实体类
- 创建application.xml文件
- 解析xml文件
- 根据反射去创建bean对象
- 将xml配置的中property节点的数据赋给创建好bean
- 测试
三、代码实现
1. 创建实体类
该实体类的set方法都要是Object,因为我们不知到从xml读取的文件是什么类型!
public class Student
private int sid;
private String name;
private String sex;
public Student()
super();
public Student(int sid, String name, String sex)
super();
this.sid = sid;
this.name = name;
this.sex = sex;
// 注意:所有set方法的参收都要是Object类型的,这里需要强转一下
public int getSid()
return sid;
public void setSid(Object sid)
this.sid = Integer.parseInt(sid.toString());
public String getName()
return name;
public void setName(Object name)
this.name = (String) name;
public String getSex()
return sex;
public void setSex(Object sex)
this.sex = (String) sex;
@Override
public String toString()
return "Student [sid=" + sid + ", name=" + name + ", sex=" + sex + "]";
2. 创建ApplicationContext.xml文件
<?xml version="1.0" encoding="UTF-8"?>
<beans>
<bean name="student" class="model.Student">
<property name="sid" value="001"></property>
<property name="name" value="name"></property>
<property name="sex" value="男"></property>
</bean>
</beans>
3. 解析xml文件、创建对象、并给对象赋值
该类通过注释进行一步步解析,可以仔细看一下注释!
public class MyApplicationContext
// 使用多线程赋值的话建议使用ConcurrentHashMap
// private Map<String,Object> beansHolder = new ConcurrentHashMap<String, Object>();
private Map<String,Object> beansMap = new HashMap<String, Object>();
private String xmlPath;
public MyApplicationContext(String xmlPath)
this.xmlPath = xmlPath;
analysisXML();
// DOM解析xml
public void analysisXML()
// 找了一个工厂
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
try
// 工厂里的一个工人
DocumentBuilder buider = factory.newDocumentBuilder();
// 工人去读取xml文件 ,然后得到了一个读取到的文件
Document document = buider.parse(xmlPath);
// 读取所有bean节点
NodeList nodeBean = document.getElementsByTagName("bean");
// 循环遍历nodeBean
for(int i = 0; i < nodeBean.getLength();i++)
// 得到所有bean属性
NamedNodeMap namedNodeMap = nodeBean.item(i).getAttributes();
// 获取bean节点
Element element = (Element)nodeBean.item(i);
// 获取bean节点下所有property元素
NodeList childNodes = element.getElementsByTagName("property");
// 将获取到的bean所有属性和bean节点下所有property元素传递到创建bean方法中继续使用
createBean(namedNodeMap,childNodes);
catch (Exception e)
e.printStackTrace();
// 创建bean
public void createBean(NamedNodeMap namedNodeMap,NodeList childNodes)
String className = null; // bean节点中的name属性值
String class_val = null; // bean节点中的class属性值
// 遍历bean的所有属性
for(int i = 0; i < namedNodeMap.getLength();i++)
Node node = namedNodeMap.item(i);
// 取出name属性值
if("name".equalsIgnoreCase(node.getNodeName()))
className = node.getNodeValue();
// 取出class属性值
if("class".equals(node.getNodeName()))
class_val = node.getNodeValue();
// 判断二者都不为空
if(!"".equals(className) && !"".equals(class_val))
// 去创建bean,并存入map集合
setBean(className,class_val);
else
System.out.println("参数为空!");
// 属性赋值(bean节点下所有property元素,bean的class属性值,bean的name属性值)
setProperty(childNodes,class_val,className);
// 注入属性值
public void setProperty(NodeList childNodes,String class_val,String className)
String name_val = null; //property元素中的name属性值
Object value_val = null; //property元素中的value属性值
// 遍历所有property元素
for(int i = 0; i < childNodes.getLength();i++)
// 获取每个property所有属性
NamedNodeMap attributes = childNodes.item(i).getAttributes();
// 遍历property的所有属性
for(int j = 0; j < attributes.getLength();j++)
// 得到一个属性节点
Node node = attributes.item(j);
if(node!= null)
// 得到name的值
if("name".equals(node.getNodeName()))
name_val = node.getNodeValue();
// 得到value的值
if("value".equals(node.getNodeName()))
value_val = node.getNodeValue();
try
// 根据bean的class属性值,获取指定类的构造器
Class<?> clazz = Class.forName(class_val);
// 去查找set方法,传入参数类型
Method method = clazz.getMethod("set"+toFirst(name_val),Object.class);
// 然后去执行set方法,指定实体类,传入该方法所需的参数
method.invoke(beansMap.get(className),value_val);
catch (Exception e)
e.printStackTrace();
// 首字母大写
public String toFirst(String str)
if(str!=null&&str.length()>0)
str=str.substring(0, 1).toUpperCase() + str.substring(1);
return str;
// 注入bean
public void setBean(String beanNname,String clazzPath)
try
// 通过反射创建bena对象
Object obj = Class.forName(clazzPath).newInstance();
// 将创建的bean存入map集合
beansMap.put(beanNname,obj);
catch (Exception e)
e.printStackTrace();
// 获取bean对象
public Object getBean(String beanName)
return beansMap.get(beanName);
3. 测试
public class MainTest
public static void main(String[] args)
MyApplicationContext context = new MyApplicationContext("src/application.xml");
Student student = (Student) context.getBean("student");
System.out.println(student.toString());
以上是关于Java通过DOM解析假装实现Spring中Bean注入的主要内容,如果未能解决你的问题,请参考以下文章