JLS , раздел 8.3.3 , содержит правила выдачи ошибки компилятора для прямой ссылки.
Для ссылки простым именем на переменную экземпляра f
, объявленную в классе C
, это ошибка времени компиляции, если:
Ссылка появляется либо в инициализаторе переменной экземпляра C
, либо в инициализаторе экземпляра C
(§8.6); и
Ссылка появляется в инициализаторе собственного декларатора f
или в точке слева от декларатора f
; и
Ссылка не в левой части выражения присваивания (§15.26); и
Самый внутренний класс, включающий ссылку, C
.
Нет условия для ошибки компилятора для ссылки из вложенного или внутреннего класса. Любопытно, что непростая ссылка может получить доступ к прямой ссылке, например,
this.x++;
Кроме того, позже в этом же разделе приведен пример, в котором явно говорится, что доступ из другого класса в порядке.
class UseBeforeDeclaration {
// Snipped
{
// Snippped
j = j + 1;
// error - right hand side reads before declaration
// Snipped
Object o = new Object() {
void foo(){ j++; }
// ok - occurs in a different class
{ j = j + 1; }
// ok - occurs in a different class
};
}
// Snipped
int j;
}
Я включил только соответствующие части - инициализатор экземпляра, который делает прямую ссылку, используя внутренний класс, плюс объявление в конце.