为何@Foo可重复标注注解接口却无法标注普通接口?
为什么
@Foo @Foo interface Intf {}是非法的? 要搞懂这个问题,得先明白Java可重复注解的底层机制:当你在同一个元素上多次使用被@Repeatable标记的注解时,编译器会自动把这些重复的注解包装进对应的容器注解(这里就是FooContainer)里。
回到你的代码细节:
@Foo被标记为@Repeatable(FooContainer.class),所以多次使用@Foo时,编译器会自动生成一个@FooContainer注解实例,把多个@Foo实例放进它的value数组中。- 但
@FooContainer的@Target(ElementType.ANNOTATION_TYPE)明确限定了它只能用于注解接口声明,不能用在普通的类、接口(非注解接口)这类ElementType.TYPE元素上。
两种场景的合法性差异就源于此:
- 对于
@Foo @Foo @interface Anno {}:编译器自动生成的@FooContainer是附加在注解接口Anno上的,完全符合@FooContainer的使用范围限制,因此合法。 - 对于
@Foo @Foo interface Intf {}:编译器需要自动生成@FooContainer并附加在普通接口Intf上,但@FooContainer的@Target不允许它作用于普通接口(属于TYPE但不是ANNOTATION_TYPE),这直接违反了注解的使用范围规则,所以整个写法是非法的。
总结一下:重复使用@Foo会触发编译器自动生成FooContainer,但FooContainer只能贴在注解接口上,普通接口没资格用这个容器注解,因此两次@Foo加在普通接口上就不合法。
内容的提问来源于stack exchange,提问作者Gosia
相关产品推荐
相关产品推荐

