简单实现Spring Ioc功能
程序员文章站
2022-03-19 15:01:52
...
1.项目结构
2.两个模拟用的注解(Service,Autowrid)
package com.madg.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 模拟Spring中的Autowrid
*/
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Autowrid {
}
package com.madg.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 模拟Spring中的Service注解
*/
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
public @interface Service {
}
3. 用于模拟待注入的实体类
package com.madg.entity;
/**
* 实体类,后期用于注入到容器
*/
public class SayClass {
public void say()
{
System.out.println("goodbye world");
}
}
4. 核心类,模拟Spring的IoC功能
package com.madg.reflact;
import com.madg.annotation.Autowrid;
import com.madg.annotation.Service;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.List;
/**
* 整个核心,模拟将数据装进容器(此处用list表示容器)
*/
public class Refection {
//装载用的容器
List<Object> objList;
public Refection()
{
objList=new ArrayList<Object>();
}
//注入
public void ref(Object object) throws ClassNotFoundException, IllegalAccessException, InstantiationException {
Class<?> clazz=object.getClass();
//判断是否带有service注解
if (clazz.isAnnotationPresent(Service.class))
{
Field[] fields=clazz.getDeclaredFields();
for (Field field:fields)
{
//判断是否带有Autowrid注解
if (field.isAnnotationPresent(Autowrid.class))
{
Class<?> entityClass=Class.forName(field.getType().getName());
//如果都符合,则实例化
Object o=entityClass.newInstance();
//装入容器
objList.add(o);
}
}
}
}
public List<Object> getList() {
return objList;
}
}
5.模拟注入
package com.madg.main;
import com.madg.annotation.Autowrid;
import com.madg.annotation.Service;
import com.madg.entity.SayClass;
/**
* 模拟注入
*/
@Service
public class SayService {
@Autowrid
SayClass sayClass;
public void say(){
sayClass.say();
}
}
6.测试
package com.madg.main;
import com.madg.entity.SayClass;
import com.madg.reflact.Refection;
import org.junit.jupiter.api.Test;
class MainTest {
@Test
void say() {
/**
* 模拟启动时加载
*/
SayService service=new SayService();
Refection refection=new Refection();
try {
/**
* 模拟启动时加载
*/
refection.ref(service);
/**
* 模拟装载完成后从容器中获取已经装载的类的实例
* 此处写的比较简单,因为知道只注入了一个实例
*/
Object o=refection.getList().get(0);
SayClass sayClass=(SayClass)o;
/**
* 调用该实例,不会报错NullPointer错误,则证明已经完成Ioc
*/
sayClass.say();
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InstantiationException e) {
e.printStackTrace();
}
}
}
7.输出