只是对IOC的简单原理进行了实现,略显简陋;
import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
import org.dom4j.io.SAXWriter;
import org.xml.sax.SAXException;
import java.beans.PropertyDescriptor;
import java.io.InputStream;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.List;
public class ClassPathXmlApplicationContext_run implements ApplicationContext{
//装载对象的集合
HashMap<String,Object> map = new HashMap<>();
//构造方法
public ClassPathXmlApplicationContext_run(String xmlPath) throws Exception {
/*1.获取指定bean*/
//解析ClassPathXmlApplicationContext.xml文件-变成流
InputStream in = ClassPathXmlApplicationContext.class.getClassLoader().getResourceAsStream(xmlPath);
//解析器
SAXReader saxReader = new SAXReader();
//解析数据流,获取根标签root
Document read = saxReader.read(in);
Element root = read.getRootElement();
//根据根标签获取指定标签集合beans
List<Element> beans = root.elements("bean");
for (Element bean:beans) {
/*2.对每个bean标签解析反射创建对象,然后添加集合map*/
//获取每个bean标签的id和class(全限定名)
String beanclass = bean.attributeValue("class");
String id = bean.attributeValue("id");
//通过反射获取对象
Class<?> aClass = Class.forName(beanclass);
Object obj = aClass.newInstance();
map.put(id,obj);
/*对每个bean标签其中的依赖注入进行反射赋值*/
//获取所有property的依赖标签---还有其他的可以根据这个思路展开
List<Element> elements = bean.elements("property");
for (Element e:elements) {
//获得数据
String name = e.attributeValue("name");
String ref = e.attributeValue("ref");
String value = e.attributeValue("value");
if(ref!=null){
//这个依赖是对象
Object o = map.get(name);
//通过反射内省获取属性描述器:就是accountDao属性的getset方法结合体
PropertyDescriptor propertyDescriptor = new PropertyDescriptor(name, aClass);
Method method = propertyDescriptor.getWriteMethod();//setAccount(AccountDao o);
//执行set方法添加
method.invoke(obj,o);
}else {
//普通类型
PropertyDescriptor propertyDescriptor = new PropertyDescriptor(name, aClass);
Method method = propertyDescriptor.getWriteMethod();//setAccount(AccountDao o);
method.invoke(obj,value);
}
}
}
}
@Override
public Object getBean(String id) {
return map.get(id);
}
}