第一步:创建两个实体类
Student.java
package com.zc.annotation.bean;
public class Student {
private String name;
private String id;
@Override
public String toString() {
return "Student [name=" + name + ", id=" + id + "]";
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
}
StuManage.java
package com.zc.annotation.bean;
public class StuManage {
public StuManage(Student student) {
super();
this.student = student;
}
public StuManage() {
super();
// TODO Auto-generated constructor stub
}
private Student student;
public Student getStudent() {
return student;
}
public void setStudent(Student student) {
this.student = student;
}
@Override
public String toString() {
return "StuManage [student=" + student + "]";
}
}
第二步:创建bean.xml,在xml文件中配置bean
<?xml version="1.0" encoding="UTF-8"?>
<beans>
<bean id="stu" class="com.zc.bean.Student">
<property name="id" value="1001"></property>
<property name="name" value="zc"></property>
</bean>
<bean id="stum" class="com.zc.bean.StuManage">
<property name="student" ref="stu"></property>
</bean>
</beans>
第三部:解析bean.xml
package com.zc.bean;
public interface ApplicationContext {
public Object getBean(String id);
}
ClassPathXmlApplicaitonContext2.java
package com.zc.bean;
import java.io.InputStream;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
public class ClassPathXmlApplicationContext2 implements ApplicationContext{
private Map<String, Object> map=new HashMap<>();
public ClassPathXmlApplicationContext2(String xml) throws Exception {
//获取xml对应的输入流对像
InputStream resourceAsStream=this.getClass().getClassLoader().getResourceAsStream(xml);
//创建dom对象
SAXReader reader=new SAXReader();
//通过输入流对象创建像对应的document对象
Document document=reader.read(resourceAsStream);
//获取根元素
Element element=document.getRootElement();
//获取根元素的所有的子元素
List<Element> beans=element.elements();
//遍历所有的子元素
for(Element bean:beans) {
//根据属性名获取对应的属性值
String id=bean.attributeValue("id");
String className=bean.attributeValue("class");
//通过反射机制去创建对应的字节码对象
Class<?> class1=Class.forName(className);
//通过字节码对象创建实例
Object object=class1.newInstance();
//把对象放到容器当中
map.put(id, object);
//获取所有的方法
Method[] allMethods = class1.getMethods();
//获取所有的参数
List<Element> pros=bean.elements();
//遍历方法
for(Method method:allMethods) {
if(method.getName().startsWith("set")) {
//判断是不是set方法
//获取属性值
for(Element pro:pros) {
//获取属性值
String proName=pro.attributeValue("name");
//判断方法和属性是否匹配
if(method.getName().substring("set".length()).equalsIgnoreCase(proName)) {
String value=pro.attributeValue("value");
if(value!=null) {
//如果匹配就执行方法
method.invoke(object, value);
}else {
method.invoke(object, map.get(pro.attributeValue("ref")));
}
}
}
}
}
}
}
@Override
public Object getBean(String id) {
return map.get(id);
}
}
4.进行测试
package com.zc.test;
import org.junit.Before;
import org.junit.Test;
import com.zc.bean.ApplicationContext;
import com.zc.bean.ClassPathXmlApplicationContext2;
import com.zc.bean.StuManage;
import com.zc.bean.Student;
public class CreateTest {
ApplicationContext ac;
/**
*@throws Exception
* @BeforeClass – 表示在类中的任意public static void方法执行之前执行
*@AfterClass – 表示在类中的任意public static void方法执行之后执行
*@Before – 表示在任意使用@Test注解标注的public void方法执行之前执行
*@After – 表示在任意使用@Test注解标注的public void方法执行之后执行
*@Test – 使用该注解标注的public void方法会表示为一个测试方法
*/
@Before
public void test() throws Exception{
ac=new ClassPathXmlApplicationContext2("beans.xml");
}
@Test
public void test2() {
Student student1= (Student) ac.getBean("stu");
System.out.println(student1);
}
@Test
public void test3() {
StuManage student4= (StuManage) ac.getBean("stum");
System.out.println(student4);
}
}
进行测试:
结果:
成功!