java注解是怎么实现的

java注解是怎么实现的,第1张

注解的使用一般是与java的反射一起使用,下面是一个例子

注解相当于一种标记,在程序中加了注解就等于为程序打上了某种标记,没加,则等于没有某种标记,以后,javac编译器,开发工具和其他程序可以用反射来了解你的类及各种元素上有无何种标记,看你有什么标记,就去干相应的事。标记可以加在包,类,字段,方法,方法的参数以及局部变量上。

自定义注解及其应用

1)、定义一个最简单的注解

public @interface MyAnnotation {

//

}

2)、把注解加在某个类上:

@MyAnnotation

public class AnnotationTest{

//

}

以下为模拟案例

自定义注解@MyAnnotation

1 package comljqtest;

2

3 import javalangannotationElementType;

4 import javalangannotationRetention;

5 import javalangannotationRetentionPolicy;

6 import javalangannotationTarget;

7

8 /

9 定义一个注解

10

11

12 @author jiqinlin

13

14 /

15 //Java中提供了四种元注解,专门负责注解其他的注解,分别如下

16

17 //@Retention元注解,表示需要在什么级别保存该注释信息(生命周期)。可选的RetentionPoicy参数包括:

18 //RetentionPolicySOURCE: 停留在java源文件,编译器被丢掉

19 //RetentionPolicyCLASS:停留在class文件中,但会被VM丢弃(默认)

20 //RetentionPolicyRUNTIME:内存中的字节码,VM将在运行时也保留注解,因此可以通过反射机制读取注解的信息

21

22 //@Target元注解,默认值为任何元素,表示该注解用于什么地方。可用的ElementType参数包括

23 //ElementTypeCONSTRUCTOR: 构造器声明

24 //ElementTypeFIELD: 成员变量、对象、属性(包括enum实例)

25 //ElementTypeLOCAL_VARIABLE: 局部变量声明

26 //ElementTypeMETHOD: 方法声明

27 //ElementTypePACKAGE: 包声明

28 //ElementTypePARAMETER: 参数声明

29 //ElementTypeTYPE: 类、接口(包括注解类型)或enum声明

30

31 //@Documented将注解包含在JavaDoc中

32

33 //@Inheried允许子类继承父类中的注解

34

35

36 @Retention(RetentionPolicyRUNTIME)

37 @Target({ElementTypeMETHOD, ElementTypeTYPE})

38 public @interface MyAnnotation {

39 //为注解添加属性

40 String color();

41 String value() default "我是林计钦"; //为属性提供默认值

42 int[] array() default {1, 2, 3};

43 Gender gender() default GenderMAN; //添加一个枚举

44 MetaAnnotation metaAnnotation() default @MetaAnnotation(birthday="我的出身日期为1988-2-18");

45 //添加枚举属性

46

47 }

注解测试类AnnotationTest

1 package comljqtest;

2

3 /

4 注解测试类

5

6

7 @author jiqinlin

8

9 /

10 //调用注解并赋值

11 @MyAnnotation(metaAnnotation=@MetaAnnotation(birthday = "我的出身日期为1988-2-18"),color="red", array={23, 26})

12 public class AnnotationTest {

13

14 public static void main(String[] args) {

15 //检查类AnnotationTest是否含有@MyAnnotation注解

16 if(AnnotationTestclassisAnnotationPresent(MyAnnotationclass)){

17 //若存在就获取注解

18 MyAnnotation annotation=(MyAnnotation)AnnotationTestclassgetAnnotation(MyAnnotationclass);

19 Systemoutprintln(annotation);

20 //获取注解属性

21 Systemoutprintln(annotationcolor());

22 Systemoutprintln(annotationvalue());

23 //数组

24 int[] arrs=annotationarray();

25 for(int arr:arrs){

26 Systemoutprintln(arr);

27 }

28 //枚举

29 Gender gender=annotationgender();

30 Systemoutprintln("性别为:"+gender);

31 //获取注解属性

32 MetaAnnotation meta=annotationmetaAnnotation();

33 Systemoutprintln(metabirthday());

34 }

35 }

36 }

枚举类Gender,模拟注解中添加枚举属性

1 package comljqtest;

2 /

3 枚举,模拟注解中添加枚举属性

4

5 @author jiqinlin

6

7 /

8 public enum Gender {

9 MAN{

10 public String getName(){return "男";}

11 },

12 WOMEN{

13 public String getName(){return "女";}

14 }; //记得有“;”

15 public abstract String getName();

16 }

注解类MetaAnnotation,模拟注解中添加注解属性

1 package comljqtest;

2

3 /

4 定义一个注解,模拟注解中添加注解属性

5

6 @author jiqinlin

7

8 /

9 public @interface MetaAnnotation {

10 String birthday();

11 }

答:你应该在类上面加上@Compnnent这个注解,注入到bean里面;或者注意 class的路径不要写错即可不出错。

一、注解策略:

(1)类级别的注解:如@Component、@Repository、@Controller、@Service以及JavaEE6的@ManagedBean和@Named注解,都是添加在类上面的类级别注解。Spring容器根据注解的过滤规则扫描读取注解Bean定义类,并将其注册到Spring IoC容器中。

(2)类内部的注解:如@Autowire、@Value、@Resource以及EJB和WebService相关的注解等,都是添加在类内部的字段或者方法上的类内部注解。SpringIoC容器通过Bean后置注解处理器解析Bean内部的注解。 Spring实现@Autowire解析和注入的核心的类是通过。

二、AutowiredAnnotationBeanPostProcessor来实现的。我们可以通过其方法列表看出,其中对字段的注入,对属性的注入,还有选择相应的构造方法来注入。

1:从构造方法的缓存中查询其构造方法。

2:若缓存中不存在,则根据反射获取所有构造方法。

3:遍历所有构造方法,查询器是否含有@Autowired属性。

4:判断Autowired注解中指定了required属性 (required属性就是判断是否强依依赖)若存在required就使用默认构造方法。

5:返回指定的构造方法 注入的时候则是通过inject方法来实现。

先来说结论吧:你说的这句话是成立的。

原因:注解本质上通过反射来实现的,我们都知道,反射是一种程序的自省机制,其实反射是破坏封装的一种方式,反射的效率很低的,对程序本身访问会造成很多的额外开销。比如你采用Spring注解,@resource标识在一个类上面,那么程序会通过反射一遍遍的调用,首先通过class得到类对象,然后调取其中的getAnnotations()方法遍历类上的注解,一遍扫描和寻找注解,这其中就会有减慢效率,这不过是一种语法糖。其实通过xml来配置更好,不过不够方便,注解的最终意义也就是方便程序员而已。

Autowired表示一个属性是否需要进行依赖注入,可以使用在属性、普通方法上、构造方法上。注解中的required属性默认是true,如果没有对象可以注入到属性,则会报出异常;

@Autowired加在某个属性上,spring会从ioc容器中找到bean对象注入到属性上,如果找到多个该类型的Bean对象,则再根据属性的名字从多个Bean对象中确认一个;

@Autowired写在set()方法上,在spring会根据方法的参数类型从ioc容器中找到该类型的Bean对象注入到方法的行参中,并且自动反射调用该方法(被@Autowired修饰的方法一定会执行),所以一般使用在set方法中、普通方法不用;

@Autowired使用在构造方法中:根据构造方法的形参、形参名,从ioc容器中找到该类型的Bean对象,注入到构造方法的形参中,并且执行该方法;

@Autowired注解在进行依赖注入的时候需要指定bean的时候,和@Qualifier注解一起使用使用@qualifier注解指定名称

//构造方法

@Autowired

public Bean03(Bean04 bean04) {

Systemoutprintln("11111111111111");

}

//属性上

@Autowired

Bean04 bean04;

//set方法

@Autowired

public void setBean04(Bean04 bean) {

thisbean04 = bean;

}

//普通方法

@Autowired

public void commonMethod(Bean04 bean04){

Systemoutprintln("普通方法的执行");

}

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

@Autowired使用在构造方法上的细节

在同一个类上有多个构造方法上使用了@Autowired,默认情况下会报错;

解决方法:可以把@Autowired的属性required设置成为false,此时spring会自己选择使用哪一种构造方法;

spring在上述情况下的选择规则:

1会优先考虑参数多的

(先ByType找到多个该类型的bean,再ByName进行注入)

2如果多个类型的bean按照ByName无法注入,则去考虑参数少的进行注入,依次类推;

3在参数个数相同、ByName,也可以注入的情况下,按照构造方法的书写顺序进行选择;

先自我介绍一下,小编13年上师交大毕业,曾经在小公司待过,去过华为OPPO等大厂,18年进入阿里,直到现在。深知大多数初中级java工程师,想要升技能,往往是需要自己摸索成长或是报班学习,但对于培训机构动则近万元的学费,着实压力不小。自己不成体系的自学效率很低又漫长,而且容易碰到天花板技术停止不前。因此我收集了一份《java开发全套学习资料》送给大家,初衷也很简单,就是希望帮助到想自学又不知道该从何学起的朋友,同时减轻大家的负担。添加下方名片,即可获取全套学习资料哦

阿里p7互联网架构师全套视频资料

微信名片

打开CSDN APP,看更多技术内容

autowired 静态方法使用_关于springboot工具类中@Autowired注入bean

springboot +mybatis 在工具类的静态方法中,需要使用mapper(其他bean也一样),所以最开始直接使用@Autowired进行了注入,代码如下: @Autowiredprivate staticMt4UsersMapper mt4UsersMapper; @Autowiredprivate staticUserBankAccountsMapper userBa

继续访问

@Autowired的原理简识

@Autowired注解是属于spring的容器配置的一个注解

继续访问

解决@Autowired注入的对象被static静态修饰的方法引用

第一种方法: public class TreeUtil { @Autowired IAreaApi AutowiredAreaApi; private static IAreaApi areaApi; @PostConstruct public void init(){ areaApi = thisAutowiredAreaApi; } } 第二种方法: @Component public class Test {

继续访问

最新发布 Spring 中 @Autowired 修饰构造方法时注意事项

1、当有且仅有1个构造方法时,Spring 都只会使用这个构造方法创建实例。2、Spring 优先选择 被 @Autowired 标注的构造方法3、当有多个构造方法同时存在时,Spring 默认选择空构造方法,若此时没有空构造方法,就会报错。4、当有多个方法同时存在时,想指定 Spring 具体用哪个构造方法,可以加上 @Autowired 注解来标识,如果此时有多个 @Autowired 同时存在,需要将所有的 required 修改成 false ,Spring 默认使用参数最多的构造方法。

继续访问

在Static方法中引用被@AutoWired修饰的属性,无法注入,报空指针异常javalangNullPointerException 、SpringBoot + Mybatis

场景:在Static方法中引用被@AutoWired修饰的属性,无法注入,报空指针异常 问题:SpringBoot + Mybatis连接数据库Bean不能注入报空指针异常 在保存到数据库时出现空指针异常 原因: 因为静态无法注入,通常我们会是在Spring框架中使用到@PostConstruct注解 该注解的方法在整个Bean初始化中的执行顺序: Constructor(构造方法) -> @Autowired(依赖注入) -> @PostConstruct(注释的方法) 解决: 网上咨询了比较

继续访问

Spring自动装配@Autowired的三种方式

转自:>

这个 按照我的理解

首先自定义注解要有自己的编译解释方法的

在这个便已解释方法中估计需要连接数据库(当然最基本的jdbc什么的)

当然连接数据库什么的涉及到配置文件

通过jdbc获取到数据库信息 把注解中的参数与数据库中的信息关联(简单的就可以存成List<Map等方式)由于注解的参数一般是类名。你可以 用反射的方式或其他方式(比如字节码什么的)来处理获取类的属性

然后 我感觉关联完了 就没啥然后了 感觉主要是在注解的编译解释方法中做写东西 当然 提高效率也可以用数据库连接池什么的

专门讲反射的书……java reflection in action 没有中文版。中文版讲这个的应该是没有的。

注解不需要专门一本书的,想要看看的话,thinking in java 中有讲解注解的这一章。第4版。

以上就是关于java注解是怎么实现的全部的内容,包括:java注解是怎么实现的、spring 注解报错No unique bean of type、JAVA注解是不是效率很低等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!

欢迎分享,转载请注明来源:内存溢出

原文地址:https://54852.com/web/9716876.html

(0)
打赏 微信扫一扫微信扫一扫 支付宝扫一扫支付宝扫一扫
上一篇 2023-05-01
下一篇2023-05-01

发表评论

登录后才能评论

评论列表(0条)

    保存