2016-10-05 3 views
2

С JAVAC 1.8.0_77 этот класс не компилируется:Почему Java lambas обрабатывается иначе, чем вложенные классы в отношении инициализации поля экземпляра?

import java.util.function.*; 
public class xx { 
    final Object obj; 

    final Supplier<Object> supplier1 = new Supplier<Object>() { 
     @Override 
     public Object get() { 
      return xx.this.obj; 
     } 
    }; 

    final Supplier<Object> supplier2 =() -> { return this.obj; }; 

    xx(Object obj) { 
     this.obj = obj; 
    } 
} 

Вот ошибка:

xx.java:12: error: variable obj might not have been initialized 
    final Supplier<Object> supplier2 =() -> { return this.obj; }; 
                 ^
1 error 

Вопросы:

  1. является генерация этой ошибки исправить в соответствии с JLS ?
  2. Если да, то в чем причина JLS, рассматривающей реализацию lamba @FunctionalInterface (supplier2) в отличие от ее эквивалентной внутренней реализации класса (supplier1) в этом отношении?

Спасибо.

ответ

1

Просматривая изменения JLS из JSR 335, это выглядит как упущение со мной:

  • Доступ к листовым конечных полей регулируется JLS Chapter 16
  • Существует раздел "Definite Assignment and Anonymous Classes", который предписывает ошибку в случай supplier1.
  • JSR 335 spec имеет только одно предельное изменение для главы 16, никогда не упоминая «лямбда» или «ссылки на методы» в этой главе.

На самом деле единственное изменение в Chap.16 является (полужирным шрифтом для добавления):

Throughout the rest of this chapter, we will, unless explicitly stated otherwise, write V to represent an in-scope (6.3) local variable or a blank final field (for rules of definite assignment) or a blank final variable (for rules of definite unassignment).

На нижней строке, компиляторы, кажется, прямо не жалуюсь в лямбда но для согласованности JLS, вероятно, следует изменить, чтобы охватить этот случай.

Редактировать:: OpenJDK уже имеет spec bug для этого, при этом мы предлагаем изменения.

+0

Спасибо за ссылку об ошибке. – Archie

+0

Ошибка спецификации была решена, javac 9-ea + 142 все еще отклоняет программу. –

+0

На ваш вопрос ответили? _ (Подсказка: прием ответа будет приятным :)) _. –