Java注解面试总结

何谓注解?

Annotation (注解) 是 Java5 开始引入的新特性,可以看作是一种特殊的注释,主要用于修饰类、方法或者变量,提供某些信息供程序在编译或者运行时使用。

注解本质是一个继承了Annotation 的特殊接口:

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.SOURCE)
public @interface Override {

}

public interface Override extends Annotation{

}

JDK 提供了很多内置的注解(比如 @Override 、@Deprecated),同时,我们还可以自定义注解。

详细解释一下Java注解

Java注解(Annotation)是一种注释语法,其可以用于向编译器、工具、框架以及其他处理注解的程序提供信息。注解可以用于类、方法、字段、参数以及其他代码元素上。和普通的代码注释不同,注解可以被编译器、IDE和其他工具读取和处理,它们可以用于自动生成代码、生成配置文件、执行单元测试以及其他一些任务。

Java注解是从Java5开始引入的,并且在Java SE 8中扩展了注解的功能。注解本质上是一个延伸的接口,其主体默认是被注解的那个类、方法、字段等元素。注解的定义格式为:@注解名(<成员名1>=<成员值1>, <成员名2>=<成员值2>,…),其中注解名就是Java中已有的、具有特殊含义的关键字。在定义注解时,可以通过@Target注解来指定该注解可以用于哪些目标上,例如:@Target(ElementType.METHOD)表示该注解只能用于方法上。

在使用注解时,可以通过反射获取注解的信息,例如,可以通过以下代码来获取某个方法上的所有注解:

Method method = someObject.getClass().getMethod("someMethod");
Annotation[] annotations = method.getAnnotations();

注解可以用来提供元数据,这些元数据可以被其他程序使用。例如,Spring框架中的@Configuration注解可以标注一个Java类,以指示该类是一个Spring配置类,Spring会读取该类中的@Bean注解,自动生成相应的Bean对象。

注解是Java语言的一个重要特性,其可以提高代码的可读性和可维护性,同时也可以增强代码的可重用性和扩展性。在Java开发中,注解已经成为了一种不可或缺的手段。

Java注解有许多内置的注解,例如:

  1. @Override:用于标识某个方法重写了父类的方法。
  2. @Deprecated:用于标识某个类或方法已经被废弃,不建议使用。
  3. @SuppressWarnings:用于告知编译器,忽略特定的警告。
  4. @FunctionalInterface:用于标识某个接口是函数式接口,在Lambda表达式中可以使用这个接口。

除了内置注解外,Java还支持创建自定义注解。创建自定义注解的步骤如下:

  1. 使用@interface关键字定义注解。
  2. 在注解中定义属性,每个属性使用@PropertyType和@PropertyDefaultValue定义数据类型和默认值。
  3. 在代码中使用自定义注解,并在注解中设置属性值。

例如,以下代码定义了一个自定义注解@MyAnnotation:

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface MyAnnotation {
    String value();
    int number() default 0;
}

该注解包含两个属性,一个是value,一个是number,其中value是一个必须要设置的字符串属性,而number是可选的整数属性,其默认值为0。可以在代码中使用@MyAnnotation注解,并设置属性值,例如:

@MyAnnotation(value = "hello", number = 123)
public void someMethod() {
    // do something
}

注解的属性可以是任意的数据类型,包括基本类型、枚举类型、类类型、注解类型以及上述类型的数组。注解的属性值可以在注解中设置,也可以使用默认值。在使用注解时,可以使用反射获取注解的属性值,例如:

Method method = someObject.getClass().getMethod("someMethod");
MyAnnotation annotation = method.getAnnotation(MyAnnotation.class);
String value = annotation.value();
int number = annotation.number();

总的来说,Java注解是一个很强大的工具,在现代Java框架和API中广泛应用。深入理解并灵活使用Java注解,可以为我们的代码带来巨大的便利和效率提升。

注解的解析方法有哪几种?

注解只有被解析之后才会生效,常见的解析方法有三种:

注解的解析方法有以下几种:

  1. 编译时解析注解:在编译时通过注解处理器解析注解,生成特定代码。

  2. 运行时解析注解:在运行时通过反射机制获取注解信息并进行处理。

  3. 自定义解析注解:通过自定义注解解析器,针对特定注解实现相应的处理逻辑。

详细解释:

  1. 编译时解析注解:

编译时注解处理器是一种插件,需要将其配置到编译器中,这样它才能在编译过程中自动来处理你的注释信息,并生成基于注解的处理代码。在 Java 中,JDK 提供了注解处理工具 javac,可以使用 javac 加上编译器选项 -processor,指定注解处理器,从而完成编译时注解的解析和处理。

编译时注解处理器可以方便的生成代码,通过将注解声明在 Java 类或者方法上,注解处理器可以在编译时自动解析注解信息,并生成符合用户需求的 Java 代码。 Java 中常见的编译时注解处理器工具有 Google 的 AutoService、Google 的 ProtoBuf 以及 JPA 中的 Hibernate。

  1. 运行时解析注解:

注解在 Java 中使用反射机制动态获取注解信息,通过反射,可以根据注解的属性类型及属性名称,获取注解的值并进行相应的处理。

运行时注解处理器可以针对特定的注解,对注解进行相应的逻辑处理,这样我们就可以在程序运行期间根据注解信息,实现一些特定的业务逻辑。

运行时注解处理器的应用场景很广,比如 Servlet 中的 @WebServlet、Spring 中的 @Transactional 等注解都是在运行时动态加载和处理的。

  1. 自定义解析注解:

与前两种方式不同的是,自定义注解解析器是通过继承 AnnotationParser 接口实现的,它是一个纯 Java 接口,并不属于 JDK 提供的工具。自定义注解解析器可以针对自定义的注解,实现用户自定义的业务逻辑处理,非常灵活。

自定义注解解析器的核心是解析注解,获取其中的 value 值,对其进行相应的处理。当程序运行时,可以使用自定义注解解析器获取指定注解的 value 值,并对其进行相应的业务处理。自定义注解解析器可以用于框架设计、AOP 面向切面编程等方面。

详细介绍一下Java枚举

Java 枚举是一种用于定义常量的数据类型。它是一组具有命名值的特殊类,可以将其视为一种“类型安全”的枚举设计模式。Java 枚举使代码更具可读性和可维护性,因为它们避免了一些常见的错误,例如大小写拼写错误和非法输入值。

一个 Java 枚举类由一个或多个枚举常量组成,每个枚举常量都有一个名称和值。枚举常量通常用大写字母表示,并用逗号分隔。

下面是一个简单的 Java 枚举类的例子:

public enum Color {
    RED,
    GREEN,
    BLUE
}

在这个例子中,我们定义了一个名为 Color 的枚举类型,它包含三个常量:REDGREENBLUE。这些常量都是 Color 类的实例。可以通过调用 Color.REDColor.GREENColor.BLUE 来引用这些实例。

Java 中的枚举类型可以具有构造函数、方法和字段。例如,我们可以向 Color 类型添加一个字段,表示该颜色的 rgb 值:

public enum Color {
    RED(255, 0, 0),
    GREEN(0, 255, 0),
    BLUE(0, 0, 255);

    private final int r;
    private final int g;
    private final int b;

    Color(int r, int g, int b) {
        this.r = r;
        this.g = g;
        this.b = b;
    }

    public int getR() {
        return r;
    }

    public int getG() {
        return g;
    }

    public int getB() {
        return b;
    }
}

在这个例子中,我们定义了一个包含 rgb 字段的 Color 枚举类型,并在每个枚举常量中传递了不同的参数。我们还为每个字段定义了 getter 方法,以便可以从外部访问这些值。

枚举类型还可以用于 switch 语句中。这是因为在 Java 中,枚举类型是一种类,并且可以用于任何需要类的地方。因此,我们可以像下面这样使用 switch 语句:

public static void main(String[] args) {
    Color color = Color.RED;
    switch (color) {
        case RED:
            System.out.println("The color is red");
            break;
        case GREEN:
            System.out.println("The color is green");
            break;
        case BLUE:
            System.out.println("The color is blue");
            break;
        default:
            System.out.println("Invalid color");
    }
}

在这个例子中,我们创建了一个名为 colorColor 枚举类型变量,并将其设置为 Color.RED。接下来,我们使用 switch 语句检查 color 变量,并打印相应的消息。

总之,Java 枚举是一种有用的编程技术,可以提高代码的可读性和可维护性。它们是类型安全的,易于使用和扩展,并可以使用 switch 语句和其他语言结构进行操作。

再举一个实际项目中比较常用的例子:

public enum Status {

    LOGIN_FAIL(201, "登陆失败"),
    LOGIN_SUCCESS(200, "登陆成功");

    private final Integer code;
    private final String message;

    Status(Integer code, String message) {
        this.code = code;
        this.message = message;
    }

    public Integer getCode() {
        return code;
    }

    public String getMessage() {
        return message;
    }
}

public static void main(String[] args) {
        System.out.println(Status.LOGIN_FAIL.getCode());
        System.out.println(Status.LOGIN_FAIL.getMessage());
    }

这个例子大家应该就比较熟悉了吧。

  • 3
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

路上阡陌

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值