#java #eclipse #static #final #introspection
#java #eclipse #статический #Финал #самоанализ
Вопрос:
Играя с самоанализом, я обнаружил интересную ситуацию, когда:
- Отображается всплывающая подсказка отладчика Eclipse
true
- println печатает
false
(обратите внимание на вывод на вкладке консоли):
Я пытаюсь установить значение private final static
поля, я думаю, я сделал это неправильно?
Что здесь на самом деле происходит?
import java.lang.reflect.*;
public class Main {
private final static boolean VAR = false; // I want to dynamically set this to true
public static void main(String[] args) throws Exception {
Field field = Main.class.getDeclaredField("VAR");
field.setAccessible(true);
Field modifiersField = Field.class.getDeclaredField("modifiers");
modifiersField.setAccessible(true);
modifiersField.setInt(field, field.getModifiers() amp; ~Modifier.FINAL);
field.set(null, true);
System.out.println(VAR);
}
}
Комментарии:
1. поскольку VAR является константой, он мог быть встроен.
Ответ №1:
Компилятор «вставляет» static final
значение. Если вы посмотрите на байт-код для println
, вы увидите что-то вроде:
iconst_0
invokevirtual java.io.PrintStream.println(boolean)
Поскольку он знает, что значение не изменится, компилятор сгенерировал код, который загружает значение 0 (для false) напрямую, не обращаясь к VAR
переменной, поэтому ваше изменение переменной игнорируется.
Из-за встраивания вы не можете полагаться на возможность изменения значения static final
переменной с отражением.