Spring注解式开发理解

JAVA注解

元注解

1、标注注解的注解,叫做元注解。@Target注解用来修饰@Component可以出现的位置。

 @Target(ElementType[]  value())// 说明属性名称是value

以下表示@Component注解可以出现在类上、属性上。

@Target(value = {ElementType.TYPE, ElementType.FIELD})

2、使用某个注解的时候,如果注解的属性名是value的话,value可以省略。如果注解的属性值是数组,并且数组中只有一个元素,大括号可以省略。

3、@Retention 也是一个元注解。用来标注@Component注解最终保留在class文件当中,并且可以被反射机制读取。(RetentionPolicy.RUNTIME) retention:保持

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
//表示注解可以出现在类上()。元注解--修饰Component注解的注解
public @interface Component {String value;}
//@Component(属性名 = 属性值, 属性名 = 属性值, 属性名 = 属性值....)
//@Component(value = "userBean")
// 如果属性名是value,value可以省略。
@Component("userBean")
public class User {
    // 编译器报错,不能出现在这里。
    //@Component(value = "test")
    //private String name;
}

模拟spring注解式开发中的包扫描机制

目前只知道一个包的名字,扫描这个包下所有的类,当这个类上有@Component注解的时候,实例化该对象,然后放到Map集合中。

public class ComponentScan {
    public static void main(String[] args){
        Map<String,Object> beanMap = new HashMap<>();
        // 目前只知道一个包的名字,扫描这个包下所有的类,当这个类上有@Component注解的时候,实例化该对象,然后放到Map集合中。
        String packageName = "com.powernode.bean";
        // 开始写扫描程序。
        // . 这个正则表达式代表任意字符。这里的"."必须是一个普通的"."字符。不能是正则表达式中的"."
        // 在正则表达式当中怎么表示一个普通的"."字符呢?使用 \. 正则表达式代表一个普通的 . 字符。
        String packagePath = packageName.replaceAll("\\.", "/");
        //System.out.println(packagePath);
        // com是在类的根路径下的一个目录。
        URL url = ClassLoader.getSystemClassLoader().getResource(packagePath);
        String path = url.getPath();//这样就拿到了绝对路径
        //System.out.println(path);
        // 获取一个绝对路径下的所有文件
        File file = new File(path);
        File[] files = file.listFiles();
        Arrays.stream(files).forEach(f -> {
            try {
                //System.out.println(f.getName());//文件类名 如:Order.class
                //System.out.println(f.getName().split("\\.")[0]);
                String className = packageName + "." + f.getName().split("\\.")[0];//包名+.+类名
                //System.out.println(className);
                // 通过反射机制解析注解
                Class<?> aClass = Class.forName(className);
                // 判断类上是否有这个注解
                if (aClass.isAnnotationPresent(Component.class)) {
                    // 获取注解
                    Component annotation = aClass.getAnnotation(Component.class);
                    String id = annotation.value();
                    // 有这个注解的都要创建对象
                    Object obj = aClass.newInstance();
                    beanMap.put(id, obj);
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        });
        System.out.println(beanMap);
    }
}

Spring注解原码

@Service原码:(其他几个Component、Repository、Controller 等差不多)

@Target({ElementType.TYPE}) //这个注解只运行出现在类上
@Retention(RetentionPolicy.RUNTIME)//该注解最终保留在class文件当中,并且可以被反射机制读取。
@Documented
@Component
public @interface Service {
    @AliasFor(//Component是老大,其他几个都是Component的别名
        annotation = Component.class
    )
    String value() default "";
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值