Можно ли аннотировать лямбда-выражение в Java 9?
Этот вопрос теперь старше 3 лет и специально адресован Java 8, с принятым ответом, также ссылаясь на Java SE 8 Final Specification.
Мне было бы интересно, изменится ли что-то в этом вопросе в Java 9: Есть ли способ аннотировать выражение лямбда, подобное аннотации соответствующего анонимного класса?
Пример:
Аннотация:
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE_USE)
public @interface MyTypeAnnotation {
public String value();
}
Рабочая аннотация анонимного класса:
Consumer<String> consumer = new @MyTypeAnnotation("Hello ") Consumer<String>() {
@Override
public void accept(String str) {
System.out.println(str);
}
};
Аннотирование выражения lamba, которое в настоящее время не работает в Java 8:
Consumer<String> myAnnotatedConsumer = @MyTypeAnnotation("Hello") (p -> System.out.println(p));
Ответы
Ответ 1
Существование вопроса Stackoverflow недостаточно, чтобы указать, что такая функция запланирована, даже если кто-то ее не рассматривает.
Если вы посмотрите на список JEP, вы увидите, что такого JEP нет даже в состоянии проекта, предлагая такие функция.
Кроме того, если вы посмотрите на текущее состояние Java 9s LambdaMetafactory
, вы увидите, что никаких изменений не было сделано для поддержки передачи метаинформацию, которая необходима для создания класса времени выполнения с записанными данными аннотации.
Кажется, есть желание добавить много метаинформации к тому, что на самом деле должно быть маленьким кусочком кода выброса, но я сомневаюсь, что разработчик языка последует за ним. Лямбда-выражения предназначены для определения функции, которая инкапсулирует поведение, а не альтернативный способ описания анонимного класса. Долгосрочная эволюция скорее приведет к реализации лямбда-выражения, которые даже менее обычного класса.
Ответ 2
В соответствии с Что нового в странице Oracle JDK 9, № Это не изменилось в Java 9.
Конечно, это не является окончательным, но JLS для Java 9 еще не выпущен.
Ответ 3
Интересно, что они аннотируют внутренний класс, который "представляет" лямбда-выражение в InnerClassLambdaMetafactory.spinInnerClass
через:
mv.visitAnnotation("Ljava/lang/invoke/LambdaForm$Hidden;", true)
Но это аннотирование класса, очевидно, не лямбда per se.
Аннотирование lambda потребует изменений в invokedynamic
и неявно LambdaMetafactory
, насколько я могу видеть, и что произойдет, когда invokedynamic не будет создавать класс для лямбда, но что-то еще, что произойдет с эти аннотации?