注解【定义+使用+读取】
来源:互联网 发布:生化危机人工智能 编辑:程序博客网 时间:2024/05/20 09:10
注解的概述
注释你还记得么?开个玩笑而已!
注释是给人看的,而注解是给程序看的!
注释是用来替代配置文件的!你回忆一下,我们以前总是要写一些配置文件,例如web.xml你还记得么?里面要写<servlet>
和<servlet-mapping>
!谁来读配置文件呢?当然是Tomcat!谁来写配置文件呢?当然是我们来写了!
在Servlet3.0中就可以使用使用注解来代替配置文件,开发者就不用再写配置文件了,而是写注解,然后Tomcat来读取注解。
注解也是类,需要定义了才能使用!
分别在Servlet3.0中有一个注解类为@WebServlet,然后我们就可以在Servlet中使用@WebServlet中使用这个注解了。这个注解就是用来替代<servlet>
了。然后Tomcat会通过反射来读取注解中的信息!
Java中的注解
Java中的注解:
- @Overrid:作用在方法上的注解。当方法不是重写父类的方法时会报错;
- @Deprecated:作用在方法上。标记该方法为作废方法(已过时);
- @SuppressWarnings:作用在方法上,压制警告。
定义注解类
定义注解类不能使用class、enum,也不能使用interface,而是使用@interface。
public @interface MyAnn{}
使用注解目标
注解可以作用在:类(接口或枚举)、属性、方法、构造器、包、参数、局部变量
package cn.itcast.annocation;@MyAnnpublic class MyClass { @MyAnn private int a; @MyAnn public MyClass() {} @MyAnn public void fun1() {} @MyAnn public void fun2(@MyAnn String s) { @MyAnn int n = 10; }}
注解的属性
定义注解时也可以给出属性,注意,属性的权限默认为public 并且,必须是public。
public @interface MyAnn { /** * 定义了两个属性 */ String value(); int value1();}
其中value就是属性!你可能会说,它是一个方法!没错,它是一个方法,但我们非要称之为属性,因为把它当做属性更加好理解。
当为注解指定属性后,那么在使用注解时就必须要给属性赋值了:
/*** 在使用注解时需要给属性赋值*/@MyAnn(value1=100,value="hello") public class MyClass {}
注解的属性还可以有默认值,在使用注解时就可以不给带有默认值的属性赋值了。但没有给出默认值的属性还是要赋值的。
public @interface MyAnn { /** * value是带有默认值的属性 */ String value() default "hello world"; int value1();}
/*** 在使用注解时,没有给出value属性,因为它有默认值,可以不赋值。* 但value1没有默认值就必须赋值。* 当然也可以给带有默认值的属性赋值。*/@MyAnn(value1=100) public class MyClass {}
在使用注解时,如果只给名为value的属性赋值,那么可以不给出属性的名称直接给出值。
public @interface MyAnn { String value() default "hello world"; int value1() default 100;}
/*** 因为所有属性都有默认值,所以没问题。*/@MyAnn() public class MyClass {}
/*** 因为所有属性都有默认值,所以可以把注解后面的圆括号省略。*/@MyAnn public class MyClass {}
/*** 给value属性赋值*/@MyAnn(value="hello") public class MyClass {}
/*** 给value1属性赋值*/@MyAnn(value1=200) public class MyClass {}
/*** 给value和value1属性赋值*/@MyAnn(value="hello",value1=200) public class MyClass {}
/*** 因为没有给出属性名称,那么就是给value属性赋值*/@MyAnn("hello annocation") public class MyClass {}
/*** 因为value属性是String类型的,所以出错!*/@MyAnn(300) public class MyClass {}
/*** 出错!因为不是给一个属性赋值,那么这时就不能再省略属性的名字。*/@MyAnn("hello",value1=200) public class MyClass {}
注解的作用目标
在定义注解时可以限制注解的作用目录!例如让注解只能作用在类和方法上。
这需要使用元注解:@Target。该注解有一个属性value,类型为ElementType[],它是枚举类型。
public @interface Target { ElementType[] value();}
public enum ElementType { TYPE,FIELD,METHOD,PARAMETED,CONSTRUCTOR,LOCAL_VARIABLE,ANNOCATION_TYPE,PACKAGE}
在定义注解时,可以使用@Target注解来限制注解的作用目标:
@Target({ElementType.TYPE, ElementType.METHOD})public @interface MyAnn {}
这样MyAnn就只能作用在类和方法上的!其中ElementType.TYPE表示类和接口。
@MyAnn()public class MyClass { /** * 出错!因为MyAnn被限制只能作用在类和方法上,不能作用在属性上。 */ @MyAnn() private int a; @MyAnn() public void fun() {}}
注解的保留策略
注解的保留策略是指,注解是只保留在源代码上,还是保留到class文件上,再或者是类在运行时,可以被类加载器加载到JVM内存中。
如果希望注解被反射,那么注解就要保留到运行时,而不是源代码或类文件上。
指定注解的保留策略需要使用元注解@Retention,它有一个value属性,类型为RetentionPolicy类型,RetentionPolicy是枚举类型:
public @interface Retention { RetentionPolicy value();}
public enum RetentionPolicy { SOURCE, CLASS, RUNTIME}
下面代码是指定注解保留到运行时
//注解保留到运行时@Retention(RetentionPolicy.RUNTIME) //注解可以作用在类或方法上@Target({ElementType.TYPE, ElementType.METHOD}) public @interface MyAnn { //String类型的value属性,默认值为hello String value() default "hello"; //int类型的value1属性,默认值为100 int value1() default 100; }
通过反射读取注解
读取注解需要使用反射来完成
/*** 保留到运行时,如果不设置为保留到运行时,那么就无法反射出来*/@Retention(RetentionPolicy.RUNTIME) @Target({ElementType.TYPE, ElementType.METHOD})public @interface MyAnn { String value() default "hello"; int value1() default 100;}
@MyAnn(value="hello world", value1=200)public class MyClass { private int a; //给value属性赋值 @MyAnn("myMethod") public void fun() {}}
public class Demo1 { public static void main(String[] args) throws Exception { Class clazz = MyClass.class; //获取类上的MyAnn类型的注解 MyAnn myAnn = (MyAnn) clazz.getAnnotation(MyAnn.class); //获取value()属性值 System.out.println(myAnn.value()); //获取value1属性值 System.out.println(myAnn.value1()); Method method = clazz.getMethod("fun"); //获取方法上的MyAnn类型的注解 MyAnn myAnn1 = method.getAnnotation(MyAnn.class); System.out.println(myAnn1.value()); System.out.println(myAnn1.value1()); }}
- 注解【定义+使用+读取】
- 使用反射读取注解
- 自定义注解定义和使用
- JavaAnnotation注解定义与使用
- 注解的定义和使用
- spring 注解源码分析-扫描和读取bean定义
- 使用注解来定义联合主键
- Servlet3.0-使用注解定义Servlet
- 使用Spring注解完成Bean的定义
- 注解类型的定义及使用
- Servlet3.0-使用注解定义Servlet
- Servlet3.0-使用注解定义Servlet
- Servlet3.0-使用注解定义过滤器(Filter)
- web3.0使用注解定义Servlet
- Servlet3.0-使用注解定义Servlet
- Servlet3.0-使用注解定义Servlet
- 使用Spring注解完成Bean的定义
- XStream 如何使用注解定义别名
- 算法设计与分析 斐波拉契数列 动态规划
- 使用Nexus搭建Maven私服
- Warning: World-writable config file '/etc/mysql/my.cnf' is ignored
- 负载均衡
- 剑指offer-2、从尾到头打印链表
- 注解【定义+使用+读取】
- Linear_regression
- css设置一个块水平和垂直居中
- 机器学习算法之朴素贝叶斯(Naive Bayes)--第一篇
- 蓝牙技术概览
- Moving Averages(6):Different Flavors
- babel
- 当一个界面有多个ViewPager的时候,如果出现某一个不显示的情况
- Maven常见问题解决