标记注释与标记接口

Posted

技术标签:

【中文标题】标记注释与标记接口【英文标题】:Marker Annotation vs Marker Interface 【发布时间】:2018-04-22 03:17:17 【问题描述】:

在阅读有关标记接口的信息时,我偶然发现了以下站点:Item 37: Use marker interfaces to define types 在这里,根据 Joshua Bloch 的说法,与 Marker 注释相比,Marker 接口有两个优点。

    标记接口定义了一种类型,该类型由 标记的类;标记注释没有。这个的存在 type 允许您在编译时捕获您无法捕获的错误 如果您使用了标记注释,则捕获直到运行时。

    标记接口相对于标记注释的另一个优势是 他们可以更准确地定位。如果注释类型是 用目标ElementType.TYPE 声明,它可以应用于任何 类或接口。假设您有一个适用的标记 仅适用于特定接口的实现。如果你定义它 作为一个标记接口,你可以让它扩展唯一的接口到 它适用,保证所有标记的类型也是 它适用的唯一接口的子类型。

好的,第一点理解了,但我不确定我是否正确理解了第二点:

如果使用目标ElementType.TYPE 声明注释类型,则它可以应用于任何类或接口。

同样,如果我有一个标记接口,那么它也可以应用于任何类或接口。关于标记注释和标记接口不是说同样的话吗? 如何更精确地定位标记界面?

第二点还提到:

您可以让 [标记接口] 扩展它适用的唯一接口,确保所有标记类型也是它适用的唯一接口的子类型。

您不能也通过使用@Inherited 元注释来实现这一点吗?

【问题讨论】:

我已经编辑了这个问题,使它更容易理解。如果我改变太多你当然可以把它改回来。 【参考方案1】:

如何更精确地定位标记界面?

您说得对,两者都可以应用于任何类型。通过“更精确地定位”,作者意味着您可以添加额外的限制,标记接口可以应用于哪些特定类型。不可能给注解添加同样精确的限制:如果一个注解被限制为ElementType.TYPE,那么它总是可以应用于所有类型。

第二点的另一部分详细介绍了如何添加这些限制。如果你有一个标记接口,你可以让它扩展另一个接口(作者称之为唯一接口),如下所示:

interface Marker extends Foo  

标记现在只能应用于实现Foo 的类型。

您不能也通过使用@Inherited 元注释来实现这一点吗?

不,@Inherited 元注释仅意味着带注释的类的任何子类型都将被视为也具有相同的注释。它没有对可以应用注解的类型施加任何限制。

【讨论】:

@kapep:作者 - Joshua Bloch 是不是想说注解不能被继承? @akshayrajkore 我编辑了问题并试图让我的答案更清楚。现在是不是更好理解了?

以上是关于标记注释与标记接口的主要内容,如果未能解决你的问题,请参考以下文章

Spring MVC @Validation 与通用控制器方法中的标记接口

什么是Java Marker Interface(标记接口)

Java 标记接口

Java标记接口

标记接口有啥好处?

什么是Java Marker Interface(标记接口)