[02] 自定义注解
1、自定义注解的方式
注解的定义和接口的创建比较相似,但注解需要以@开头,用@interface来声明一个注解,其中:
- 每一个方法实际上是声明了一个配置参数
- 方法的名称就是参数的名称,方法不带参数,可以省略public
- 返回值类型就是参数的类型(返回值类型只能是基本类型、Class、String、enum)
- 可以通过default来声明参数的默认值
定义注解的基本格式:
public @interface 注解名 {定义体}
1
1
public @interface 注解名 {定义体}
注解参数的可支持数据类型:
- 所有基本数据类型
- String类型
- Class类型
- enum类型
- Annotation类型
- 以上类型的数组
2、自定义注解示例
2.1 定义自定义注解
/**
* 水果名称注解
*/
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface FruitName {
String value() default "";
}
9
1
/**
2
* 水果名称注解
3
*/
4
ElementType.FIELD) (
5
RetentionPolicy.RUNTIME) (
6
7
public @interface FruitName {
8
String value() default "";
9
}
/**
* 水果颜色注解
*/
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface FruitColor {
/**
* 颜色枚举
*/
public enum Color {BULE, RED, GREEN}
/**
* 颜色属性
*/
public Color fruitColor() default Color.GREEN;
}
17
1
/**
2
* 水果颜色注解
3
*/
4
ElementType.FIELD) (
5
RetentionPolicy.RUNTIME) (
6
7
public @interface FruitColor {
8
/**
9
* 颜色枚举
10
*/
11
public enum Color {BULE, RED, GREEN}
12
13
/**
14
* 颜色属性
15
*/
16
public Color fruitColor() default Color.GREEN;
17
}
2.2 使用自定义注解
/**
* 苹果类
*/
public class Apple {
/**
* 苹果名称
*/
@FruitName("apple")
private String appleName;
/**
* 苹果颜色
*/
@FruitColor(fruitColor = FruitColor.Color.RED)
private String appleColor;
public String getAppleName() {
return appleName;
}
public void setAppleName(String appleName) {
this.appleName = appleName;
}
public String getAppleColor() {
return appleColor;
}
public void setAppleColor(String appleColor) {
this.appleColor = appleColor;
}
}
34
1
/**
2
* 苹果类
3
*/
4
public class Apple {
5
6
/**
7
* 苹果名称
8
*/
9
"apple") (
10
private String appleName;
11
12
/**
13
* 苹果颜色
14
*/
15
fruitColor = FruitColor.Color.RED) (
16
private String appleColor;
17
18
19
public String getAppleName() {
20
return appleName;
21
}
22
23
public void setAppleName(String appleName) {
24
this.appleName = appleName;
25
}
26
27
public String getAppleColor() {
28
return appleColor;
29
}
30
31
public void setAppleColor(String appleColor) {
32
this.appleColor = appleColor;
33
}
34
}
到这里,其实注解还没有发挥什么真正的作用,它并没有实际影响到我们的代码。注解真正的作用,主要还是在于注解的处理方法上。
3、关于注解元素的默认值
注解元素必须有确定的值,要么在定义注解的默认值中指定,要么在使用注解时指定,非基本类型的注解元素的值不可为null。因此, 使用空字符串或0作为默认值是一种常用的做法。
这个约束使得处理器很难表现一个元素的存在或缺失的状态,因为每个注解的声明中,所有元素都存在,并且都具有相应的值,为了绕开这个约束,我们只能定义一些特殊的值,例如空字符串或者负数,一次表示某个元素不存在,在定义注解时,这已经成为一个习惯用法。
如下示例:
/**
* 苹果供应商注解
*/
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface FruitProvider {
/**
* 供应商编号
*/
public int id() default -1;
/**
* 供应商名称
*/
public String name() default "";
/**
* 供应商地址
*/
public String address() default "";
}
x
1
/**
2
* 苹果供应商注解
3
*/
4
ElementType.FIELD) (
5
RetentionPolicy.RUNTIME) (
6
7
public @interface FruitProvider {
8
9
/**
10
* 供应商编号
11
*/
12
public int id() default -1;
13
14
/**
15
* 供应商名称
16
*/
17
public String name() default "";
18
19
/**
20
* 供应商地址
21
*/
22
public String address() default "";
23
24
}