为什么注释属性的值应该是常量表达式?

时间:2013-02-18 07:09:45

标签: java annotations

我正在使用以下代码

 @UIUnitTimeout(8*60*1000) // works
 @UIUnitTimeout(TimeUnit.MINUTES.toMillis(8)) // does not work

我知道根据JLS,只允许常量表达式作为注释属性的值。但为什么?如果数据类型匹配,为什么它不够?如果要在运行时评估表达式,是否有任何可能出错的地方?每个规范都有逻辑推理吗?

2 个答案:

答案 0 :(得分:9)

注释类似于类型的类型扩展或元数据。

因为java是静态类型语言(意味着类型在编译时是已知的),所以在编译时也可以知道注释属性数据(元数据) - 您正在定义/声明有关注释的数据(扩展) )。

作为纯粹实用的一点,对于annotation processing,这是一个编译时(可选)步骤,属性数据必须在编译时才知道 - 你还没有达到运行时环境,但您需要属性数据。

答案 1 :(得分:3)

注释预处理需要在执行带注释的代码之前知道注释的值。此外,注释定义本身也是使用@Retention进行分配的,其值为RetentionPolicy(如果未指定,则默认为CLASS)。

因此,有3种不同的“种类”注释,只有那些声明为RUNTIME的注释在程序执行时才可用。 (但它们的值必须是常量,以便在不执行相关代码的情况下保持定义。)

  

CLASS注释将由编译器记录在类文件中   但在运行时不需要由VM保留。

     

RUNTIME注释将由编译器记录在类文件中并保留   VM在运行时,因此可以反射性地读取它们。

     

SOURCE编译器将丢弃注释。