Какая концепция: Тип - Элемент - Зеркало
Я работаю с обработкой аннотации Java 6, то есть тем, что можно найти в javax.annotation.processing
(а не в Java 5 APT).
Интересно, какова концептуальная разница между различными классами Element
, Type
и Mirror
. Поскольку я действительно не понимаю этого, трудно эффективно программировать обработчик аннотации. Существуют различные методы, которые "конвертируют" между этими понятиями, но я не совсем уверен, что я делаю при их использовании.
Так, например, позвольте мне иметь экземпляр AnnotationMirror
.
Когда я вызываю getAnnotationType()
, я получаю экземпляр DeclaredType
(который по какой-либо причине реализует TypeMirror
).
Тогда я могу называть asElement()
на этом и получить экземпляр Element
.
Что случилось?
Ответы
Ответ 1
Объект типа javax.lang.model.element.AnnotationMirror
представляет аннотацию в вашем коде.
Объявленный тип представляет класс аннотации.
Его элемент является общим классом (см. http://java.sun.com/javase/6/docs/api/javax/lang/model/element/TypeElement.html для получения дополнительной информации по этому вопросу). Элементом может быть общая версия класса, например List
, где, поскольку объявленный тип является параметризованной версией, например List<String>
. Однако я не уверен, что в классах аннотаций могут использоваться дженерики, и, таким образом, различие может быть неактуальным в этом контексте.
Например, скажем, у вас есть следующий метод JUnit4:
@Test(expected = MyException.class)
public void myTest() {
// do some tests on some class...
}
AnnotationMirror представляет @Test(expected = NullPointerException.class)
. Объявленный тип - это класс org.junit.Test
. Элемент более или менее совпадает с тем, что не существует никаких дженериков.
Ответ 2
Фактически существует перекрытие между этими понятиями.
-
Element
моделирует статическую структуру программы, то есть пакеты, классы, методы и переменные. Просто подумайте обо всем, что вы видите в проводнике пакетов Eclipse.
-
Type
моделирует статически определенные ограничения типа программы, т.е. типы, параметры типового типа, групповые символы общего типа. Просто подумайте обо всем, что является частью объявлений типа Java.
-
Mirror
- альтернативное понятие для размышлений Гилада Брача и Дэйва Унгага, первоначально разработанного для "Я", диалекта Smalltalk на основе прототипов. Основная идея состоит в том, чтобы отделить запросы от структуры кода (а также манипуляции со структурой структуры, увы, недоступной в Java) из объектов домена. Поэтому, чтобы запросить объект о его методах, вместо вызова #getClass
вы должны спросить систему о зеркале, через которое вы можете увидеть отражение объекта. Благодаря этому разделению вы также можете зеркалировать классы, которые не загружаются (как в случае обработки аннотации), или даже классы на удаленном изображении. Например, V8 (механизм Javascript Google) использует зеркала для отладки кода Javascript, который работает в другом пространстве объекта.
Ответ 3
Этот документ может помочь в разработке дизайна обработки аннотации Java 6:
Гилад Брача и Дэвид Унгар. Зеркала: Принципы проектирования для метауровня Объекты объектно-ориентированных Языки программирования. В Proc. из ACM Conf. по объектно-ориентированным Программирование, системы, языки и Приложения, октябрь 2004 г.