Java ek açıklama üyeleri için hangi türler kullanılabilir?


238

Bugün bu dokümantasyonun ardından ilk ek açıklama arayüzümü oluşturmak istedim ve bu derleyici hatasını aldım

Invalid type for annotation member":
public @interface MyAnnotation {
    Object myParameter;
    ^^^^^^
}

Açıkçası Objectbir ek açıklama üyesi olarak kullanılamaz. Maalesef hangi türlerin genel olarak kullanılabileceği hakkında hiçbir bilgi bulamadım.

Bu deneme yanılma kullanarak öğrendim:

  • String → Geçerli
  • int → Geçerli
  • Integer → Geçersiz (Şaşırtıcı bir şekilde)
  • String[] → Geçerlilik (Şaşırtıcı bir şekilde)
  • Object → Geçersiz

Belki birileri hangi türlere izin verildiğine ve nedenine ışık tutabilir.


büyük olasılıkla ek açıklamaya göre değişir - lütfen yazmaya çalıştığınız kodu gösterin.
djna

2
Soruya eklendi. Ama farklı olduğunu düşünmüyorum.
Daniel Rikowski

Yanıtlar:


324

JLS'nin bölüm 9.6.1'inde belirtilmiştir . Ek açıklama üye türleri şunlardan biri olmalıdır:

  • ilkel
  • sicim
  • bir numaralandırma
  • başka bir Ek Açıklama
  • Sınıf
  • yukarıdakilerden herhangi birinin bir dizisi

Kısıtlayıcı görünüyor, ancak şüphesiz bunun nedenleri var.

Ayrıca, çok boyutlu dizilerin (ör. String[][]) Yukarıdaki kural tarafından dolaylı olarak yasaklandığını da unutmayın .

Açıklandığı gibi Sınıfı'nın Diziler izin verilmez bu cevap .


33
Bu sayfaları / belgeleri nasıl bulur? StackOverlow ve birçok Java soru sormadan önce her zaman google yemin yemin JSL bir bağlantı benim soru cevap bir bağlantı gönderir. Neden bu sayfaları Google üzerinden bulamıyorum ?!
Daniel Rikowski

10
JLS çok google dostu değil. Sadece orada olduğunu bilmen gerek.
skaffman

1
Aynı bilgiler de güneşin sitesinde açıklama kılavuzunda mevcuttur (Googling buldun): java.sun.com/j2se/1.5.0/docs/guide/language/annotations.html
wds

1
Evet, o sayfayı da buldum, ama tüm düzyazı metinlerinde gizlenmiş olan bu cümleyi kaçırmış olmalıyım. Daha tablo veya liste benzeri bir şey aradım.
Daniel Rikowski

13
Yukarıdaki listede eksik olan "Ek Açıklama" dır. Başka bir ek açıklama veya başka bir ek açıklama dizisi içeren bir ek açıklamanız olabilir.
Matt

58

Mevcut Tipler için Skaffman'a katılıyorum.

Ek kısıtlama: derleme zamanı sabiti olmalıdır .

Örneğin, aşağıdakiler yasaktır:

@MyAnnot("a" + myConstantStringMethod())
@MyAnnot(1 + myConstantIntMethod())

31

Ayrıca ek açıklamaların kendilerinin ek açıklama tanımının bir parçası olabileceğini unutmayın. . Bu, bazı ek açıklama yuvalamalarına olanak tanır - bir ek açıklamanın birçok kez sunulmasını istediğiniz durumlarda kullanışlıdır.

Örneğin:

@ComplexAnnotation({
    @SimpleAnnotation(a="...", b=3),
    @SimpleAnnotation(a="...", b=3),
    @SimpleAnnotation(a="...", b=3)
})
public Object foo() {...}

nerede SimpleAnnotationolduğunu

@Target(ElementType.METHOD)
public @interface SimpleAnnotation {
    public String a();
    public int b();
)

ve ComplexAnnotationolduğu

@Target(ElementType.METHOD)
public @interface ComplexAnnotation {
    public SimpleAnnotation[] value() default {};
)

Alınan örnekler: http://web.archive.org/web/20131216093805/https://blogs.oracle.com/toddfast/entry/creating_nested_complex_java_annotations

(orijinal URL: https://blogs.oracle.com/toddfast/entry/creating_nested_complex_java_annotations )


6
Java 8 ile @Repeatableartık buna gerek yok.
Mordechai

11

Ek açıklamalar kavramı, ek açıklamada karmaşık veri türlerine sahip olamayacağınızı fark edene kadar projemin tasarımına çok iyi uyuyor. Bu sınıfın somutlaştırılmış bir nesnesinden ziyade, somutlaştırmak istediklerimin sınıfını kullanarak etrafta dolaştım. Mükemmel değil, ama java nadiren.

@interface Decorated { Class<? extends PropertyDecorator> decorator() }

interface PropertyDecorator { String decorate(String value) }

class TitleCaseDecorator implements PropertyDecorator {
    String decorate(String value)
}

class Person {
    @Decorated(decorator = TitleCaseDecorator.class)
    String name
}
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.