java手写_Java手写简单的IOC实现

一、IOC定义

控制反转(Inversion of Control,英文缩写为IoC)。

定义很难理解,下面说下我个人的理解:

1、控制,即对象创建的控制,Java是面向对象的语言,传统的创建对象都是手动new一个对象,是由程序员自己控制的。

2、反转则是把创建对象的过程交给容器去创建。

二、思路

既然是把创建对象交给容器去创建,那么首先我们必须要知道我们对哪些类创建对象交给容器去管理。

所以就有以下类:

①、自定义IOC注解,只有注解的才能被容器管理

②、要被容器管理的对象那些类

③、容器类,管理对象

④、容器工厂类

⑤、创建对象的类,把创建好的对象交给容器管理

⑥、扫描类,只有被扫描到的类才能被容器管理

⑦、测试类

三、源码实现

1、注解Ioc类

import java.lang.annotation.*;

/**

* @Author: liudq

* @Description: 自定义IOC注解

* @Date: create in 2017/10/29 14:22

*/

@Documented

@Retention(RetentionPolicy.RUNTIME)

@Target({ElementType.METHOD,ElementType.FIELD,ElementType.TYPE})

public @interface Ioc {

boolean isCreate() default true;

}

2、被管理对象的类

①、学生类

/**

* @Author: liudq

* @Description: 学生

* @Date: create in 2017/10/29 14:22

*/

@Ioc

public class Student {

private long id;

private String name;

private int age;

private boolean sex;

@Ioc

private Address address;

public long getId() {

return id;

}

public void setId(long id) {

this.id = id;

}

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public int getAge() {

return age;

}

public void setAge(int age) {

this.age = age;

}

public boolean isSex() {

return sex;

}

public void setSex(boolean sex) {

this.sex = sex;

}

public Address getAddress() {

return address;

}

public void setAddress(Address address) {

this.address = address;

}

}

②、地址类

/**

* @Author: liudq

* @Description: 地址类

* @Date: create in 2017/10/29 14:22

*/

@Ioc

public class Address {

private long id;

@Ioc

private Province province;

@Ioc

private City city;

private String detail;

public long getId() {

return id;

}

public void setId(long id) {

this.id = id;

}

public Province getProvince() {

return province;

}

public void setProvince(Province province) {

this.province = province;

}

public City getCity() {

return city;

}

public void setCity(City city) {

this.city = city;

}

public String getDetail() {

return detail;

}

public void setDetail(String detail) {

this.detail = detail;

}

}

③、省类

/**

* @Author: liudq

* @Description: 省

* @Date: create in 2017/10/29 14:22

*/

@Ioc

public class Province {

private long id;

private String name;

public long getId() {

return id;

}

public void setId(long id) {

this.id = id;

}

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

}

④、市类

/**

* @Author: liudq

* @Description: 市

* @Date: create in 2017/10/29 14:22

*/

@Ioc

public class City {

private long id;

private String name;

@Ioc

private Province province;

public long getId() {

return id;

}

public void setId(long id) {

this.id = id;

}

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public Province getProvince() {

return province;

}

public void setProvince(Province province) {

this.province = province;

}

}

3、容器类

/**

* @Author: liudq

* @Description: Bean容器

* @Date: create in 2017/10/29 14:22

*/

public interface BeanContext {

T getBean(String name) throws Exception;

T getBean(Class clz);

void addBean(Class clz);

void addBean(String clz);

}

import java.util.HashMap;

import java.util.Map;

/**

* @Author: liudq

* @Description: 默认Bean容器类

* @Date: create in 2017/10/29 14:22

*/

public class DefaultBeanContext implements BeanContext {

private Map context = new HashMap();

private Bean instance = new Bean();

@Override

public T getBean(String name) {

name = analysisName(name);

return (T) context.get(name);

}

@Override

public T getBean(Class clz) {

return getBean(clz.getName());

}

@Override

public void addBean(Class clz) {

addBean(clz.getName());

}

@Override

public void addBean(String name) {

String key = analysisName(name);

Object bean = context.get(key);

if (bean == null){

bean = instance.createObject(name);

context.put(key,bean);

}

}

public static String analysisName(String name){

if (name == null || "".equals(name)){

throw new NullPointerException("类名称不能为空!");

}

String[] split = name.split("\\.");

if (split != null && split.length > 0){

String s = split[split.length - 1];

String first = s.substring(0,1).toLowerCase();

String end = s.substring(1,s.length());

return first+end;

}

String first = name.substring(0,1).toLowerCase();

String end = name.substring(1,name.length());

return first+end;

}

}

4、容器工厂类

/**

* @Author: liudq

* @Description: Bean容器工厂类

* @Date: create in 2017/10/29 14:22

*/

public class BeanContextFactory {

private static BeanContext beanContext = new DefaultBeanContext();

public static BeanContext createBeanContext(){

return beanContext;

}

}

5、创建对象的类

import java.lang.reflect.Constructor;

import java.util.*;

/**

* @Author: liudq

* @Description: 创建bean

* @Date: create in 2017/10/29 14:22

*/

public class Bean {

public T createObject(Class clz){

return createObject(clz,null,null);

}

public T createObject(Class clz, List> constructTypes, List constructArgs){

Class> aClass = resolveInterface(clz);

return (T)instance(aClass, constructTypes, constructArgs);

}

public Object createObject(String name) {

Object o = null;

try {

Class> aClass = Class.forName(name);

o = aClass.newInstance();

} catch (Exception e) {

e.printStackTrace();

}

return o;

}

protected T instance(Class clz, List> constructTypes, List constructArgs) {

try {

Constructor constructor;

if (constructTypes == null || constructArgs == null){

constructor = clz.getDeclaredConstructor();

return constructor.newInstance();

}

constructor = clz.getDeclaredConstructor(constructTypes.toArray(new Class[constructArgs.size()]));

return constructor.newInstance(constructArgs.toArray(new Object[constructArgs.size()]));

} catch (Exception e) {

e.printStackTrace();

throw new RuntimeException("创建对象异常");

}

}

protected Class> resolveInterface(Class> type) {

Class> classToCreate;

if (type == List.class || type == Collection.class || type == Iterable.class) {

classToCreate = ArrayList.class;

} else if (type == Map.class) {

classToCreate = HashMap.class;

} else if (type == SortedSet.class) {

classToCreate = TreeSet.class;

} else if (type == Set.class) {

classToCreate = HashSet.class;

} else {

classToCreate = type;

}

return classToCreate;

}

}

6、扫描类

import java.lang.reflect.Field;

/**

* @Author: liudq

* @Description: 扫描Bean

* @Date: create in 2017/10/29 14:22

*/

public class Scan {

private BeanContext beanContext;

public Scan(BeanContext beanContext){

this.beanContext = beanContext;

}

public BeanContext getBeanContext() {

return beanContext;

}

public void setBeanContext(BeanContext beanContext) {

this.beanContext = beanContext;

}

public void scan(Class> clz ){

scan(new Class[]{clz});

}

public void scan(Class>[] clzs){

for (Class clz : clzs){

Ioc ioc = (Ioc) clz.getAnnotation(Ioc.class);

if (ioc != null){

if (ioc.isCreate()){

beanContext.addBean(clz);

System.out.println("类"+clz.getName()+" 被注册");

}

}

Field[] declaredFields = clz.getDeclaredFields();

if (declaredFields != null){

for (Field field : declaredFields){

Ioc annotation = field.getAnnotation(Ioc.class);

if (annotation != null){

if (annotation.isCreate()){

Class> fieldType = field.getType();

beanContext.addBean(fieldType);

System.out.println(clz.getName()+"里的"+field.getName()+"字段的类型"+fieldType.getName()+" 被注册");

try {

field.setAccessible(true);

field.set(beanContext.getBean(clz),beanContext.getBean(fieldType));

} catch (IllegalAccessException e) {

e.printStackTrace();

}

}

}

}

}

}

}

}

7、测试类

/**

* @Author: liudq

* @Description: 测试

* @Date: create in 2017/10/29 14:22

*/

public class App {

public static void main(String[] args) {

BeanContext beanContext = BeanContextFactory.createBeanContext();

Scan scan = new Scan(beanContext);

scan.scan(new Class[]{Student.class,Address.class,Province.class,City.class});

Student student = beanContext.getBean(Student.class);

System.out.println(student.getAddress().getProvince().getName());

}

}

四、目的

IOC的主要目的是解耦合。

五、浅谈

这里只是一个简单的IOC的实现,主要技术是Java的反射。希望有助于大家对IOC的理解。

实践是检验真理的唯一标准。只有我们自己多敲代码多测试才能加深我们对程序的理解。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值