Java注解使用! 转载// 项目中页数这么用,已经很深入了
2022/1/14 1:03:46
本文主要是介绍Java注解使用! 转载// 项目中页数这么用,已经很深入了,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!
先来一个例子
class Father { public void f() {} } public class Son extends Father{ @Override public void f() {} }
- 当子类重写父类的方法的时候,上面会出现一个
@Override
,这就是一个注解
@Controller public class StudentController {
- 框架中的
@Controller
也是一个注解
什么是注解
public interface Annotation { boolean equals(Object obj); int hashCode(); String toString(); Class<? extends Annotation> annotationType(); }
- 注解是一个接口
- 从某方面看,注解的作用就像修饰符(public,final,static)一样
- 程序可以通过反射来获取指定程序元素的Annotion,然后通过Annotion来获取注解里面的元数据。
注解的种类
- JDK内置系统注解
- 元注解,用于'修饰'注解
- 自定义注解
JDK内置系统注解
@Override
- 上面的例子已经展示,这个注解的作用是用于修饰覆盖了父类的方法
@Deprecated
- 这个注解是用来修饰已经过时的方法
- 可以看到当方法用@Deprecated修饰,然后使用这个方法的时候,编译器会提醒这个方法已经过时
@SuppressWarnnings
- 用于忽略编译器警告信息,告诉编译器停止对此方法的警告。
元注解
@Target
- 作用:被描述的注解可以用在什么地方
- 参数值
ElementType | 含义 |
---|---|
ElementType | 含义 |
ANNOTATION_TYPE | 注解类型声明 |
CONSTRUCTOR | 构造方法声明 |
FIELD | 字段声明(包括枚举常量) |
LOCAL_VARIABLE | 局部变量声明 |
METHOD | 方法声明 |
PACKAGE | 包声明 |
PARAMETER | 参数声明 |
TYPE | 类、接口(包括注解类型)或枚举声明 |
import java.lang.annotation.Target; import java.lang.annotation.ElementType; @Target(ElementType.FIELD) public @interface MyAnnotation { }
- 上面是自定义的一个注解,用了一个@Target来修饰,表明这个自定义注解可以用来修饰域
@Retention
- 作用:指示注释类型的注释要保留多久
- 参数值
RetentionPoicy | 意义 |
---|---|
SOURCE | 源文件中保留,比如@Override,用于与编译器交互 |
CLASS | source,Class文件保留,用于编译时生成额外的文件 |
RUNTIME | sorce,class文件,运行时保留 |
@Documented
- 作用:指示某一类型的注释将通过 javadoc 和类似的默认工具进行文档化
- 被@Documented修饰的注解会生成到javadoc中
import java.lang.annotation.Documented; @Documented public @interface Demo { }
- 打开cmd,然后执行javadoc Demo.java,然后可以看到这个注解生成到了javadoc
@Inherited
- 作用:指示注释类型被自动继承。可以让子类对象使用getAnnotations()获取父类@Inherited修饰的注解。
@Inherited @Retention( RetentionPolicy.RUNTIME) @Target(ElementType.TYPE) public @interface MyAnnotation { String msg() default "jiajun"; } @MyAnnotation class Father { } class son extends Father{ } public class Demo6 { public static void main(String[] args) { Father f=new son(); System.out.println(Arrays.toString(f.getClass().getAnnotations())); } } //输出:[@MyAnnotation(msg=jiajun)]
自定义注解
格式
- public @interface 注解名 {定义体}
@Retention源码
@Documented @Retention(RetentionPolicy.RUNTIME) @Target(ElementType.ANNOTATION_TYPE) public @interface Retention { /** * Returns the retention policy. * @return the retention policy */ RetentionPolicy value(); }
- 可以看到注解方法返回值是RetentionPolicy枚举类型
使用
- 用@interface(区别于interface)来声明一个注解
- 使用@interface定义注解的时候,自动继承了Annotation接口
- 用元注解修饰自定义注解
- 定义体里面可以定义一些参数成员,default设置默认参数值
- 使用注解的时候,传值方式(msg=""),当参数名是value的时候,可以直接用("666")的形式传值。
- 当没有传值的时候,
@MyAnnotation()
,获取到的参数值是默认值
实验
@Retention( RetentionPolicy.RUNTIME) @Target(ElementType.TYPE) public @interface MyAnnotation { String msg() default "jiajun"; } @MyAnnotation(msg="666") class Test1 {} public class Test2 { public static void main(String[] args) { Test1 t=new Test1(); Class c=t.getClass(); MyAnnotation ma = (MyAnnotation) c.getAnnotation(MyAnnotation.class); System.out.println(ma.msg()); } }
- 自定义了一个MyAnnotation注解,用Retention注解声明注解的生命周期,和Target修饰该注解的修饰范围
- Test1类用自定义的注解修饰,通过Class获取相关信息。当Rention修饰的不是RUNTIME的时候,不能获得相关信息
访问注解
访问类注解
@Retention( RetentionPolicy.RUNTIME) @Target(ElementType.TYPE) public @interface MyAnnotation { String name() default "jiajun"; } @MyAnnotation(name="jiajun") public class Test { } public static void main(String[] args) { Class clazz = Test.class; Annotation[] annotations = clazz.getAnnotations(); for(Annotation annotation : annotations){ if(annotation instanceof MyAnnotation){ MyAnnotation myAnnotation = (MyAnnotation) annotation; System.out.println("name: " + myAnnotation.name()); } } }
访问方法注解
@Retention( RetentionPolicy.RUNTIME) @Target(ElementType.METHOD) public @interface MyAnnotation { String name() default "jiajun"; } public class Test { @MyAnnotation(name="jiajun") public void doSomething(){} } public class Demo { public static void main(String[] args) { Class clazz=Test.class; Method[] methods=clazz.getMethods(); for(Method method :methods) { if(method.getName()=="doSomething") { Annotation annotation = method.getAnnotation(MyAnnotation.class); if(annotation instanceof MyAnnotation){ MyAnnotation myAnnotation = (MyAnnotation) annotation; System.out.println("name: " + myAnnotation.name()); } } } } }
访问参数注解
@Retention( RetentionPolicy.RUNTIME) @Target(ElementType.PARAMETER) public @interface MyAnnotation { String name() default "jiajun"; } public class Test { public static void doSomething( @MyAnnotation(name="jiajun") String parameter){ } } public class Demo { public static void main(String[] args) { Class clazz=Test.class; Method[] methods=clazz.getMethods(); for(Method method :methods) { if(method.getName()=="doSomething") { Annotation[][] parameterAnnotations = method.getParameterAnnotations(); Class[] parameterTypes = method.getParameterTypes(); int i=0; for(Annotation[] annotations : parameterAnnotations){ Class parameterType = parameterTypes[i++]; for(Annotation annotation : annotations){ if(annotation instanceof MyAnnotation){ MyAnnotation myAnnotation = (MyAnnotation) annotation; System.out.println("param: " + parameterType.getName()); System.out.println("name : " + myAnnotation.name()); } } } } } } }
- 每个方法有n个参数,每个参数包含一个注解数组,因此getParameterAnnotations()返回的是一个二维数组
我是一个大懒逼!
我是一个大懒逼
我是一个大懒逼
我是一个大懒逼
我是一个大懒逼
作者:jiajun 出处: http://www.cnblogs.com/-new/
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。如果觉得还有帮助的话,可以点一下右下角的【推荐】,希望能够持续的为大家带来好的技术文章!想跟我一起进步么?那就【关注】我吧。
这篇关于Java注解使用! 转载// 项目中页数这么用,已经很深入了的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!
- 2024-11-30java最新版本是什么,有什么特性?-icode9专业技术文章分享
- 2024-11-30[开源]27.8K star!这款 Postman 替代工具太火了!
- 2024-11-30Gzip 压缩入门教程:轻松掌握文件压缩技巧
- 2024-11-29开源工具的魅力:让文档管理更“聪明”
- 2024-11-29Release-it开发入门教程
- 2024-11-29Rollup 插件入门教程:轻松掌握模块打包
- 2024-11-29从零到一,产品经理如何玩转项目管理和团队协作
- 2024-11-29如何通过精益生产管理工具帮助项目团队实现精准进度控制?
- 2024-11-29低代码应用开发课程:新手入门与基础教程
- 2024-11-29入门指南:全栈低代码开发课程