Каноническая реализация JVM от Sun применяет довольно изощренную оптимизацию к байт-коду, чтобы получить почти нативную скорость выполнения после того, как код был запущен несколько раз.
Вопрос в том, почему этот скомпилированный код не кэшируется на диск для последующего использования одной и той же функции / класса?
В его нынешнем виде каждый раз, когда выполняется программа, JIT-компилятор запускается заново, а не использует предварительно скомпилированную версию кода. Разве добавление этой функции не привело бы к значительному увеличению начального времени выполнения программы, когда байт-код, по сути, интерпретируется?
Ответы:
Не прибегая к сокращению ссылки, которую опубликовал @MYYN, я подозреваю, что это связано с тем, что оптимизация, которую выполняет JVM, не статическая, а скорее динамическая, на основе шаблонов данных, а также шаблонов кода. Вероятно, что эти шаблоны данных изменятся в течение жизненного цикла приложения, в результате чего кэшированные оптимизации будут менее оптимальными.
Таким образом, вам понадобится механизм, чтобы установить, были ли сохраненные оптимизации оптимальными, и в этот момент вы могли бы просто повторно оптимизировать на лету.
источник
JVM Oracle действительно документирована для этого - цитируя Oracle,
Я не знаю, почему все сложные реализации виртуальных машин не предлагают подобных вариантов.
источник
Обновление существующих ответов - в Java 8 есть JEP, посвященный решению этой проблемы:
=>
JEP 145: Кэш-скомпилированный код. Новая ссылка .На очень высоком уровне заявленная цель :
Надеюсь это поможет.
источник
Excelsior JET имеет кэширующий JIT-компилятор, начиная с версии 2.0, выпущенной еще в 2001 году. Более того, его компилятор AOT может перекомпилировать кеш в одну DLL / общий объект, используя все оптимизации.
источник
Я не знаю настоящих причин, так как не участвовал в реализации JVM, но могу придумать некоторые правдоподобные:
Но я на самом деле предполагаю, и, как вы видите, я не думаю, что какие-либо из моих причин действительно мешают шоу. Я полагаю, что Sun просто не считает эту поддержку приоритетной, и, возможно, моя первая причина близка к истине, поскольку выполнение этого обычно может также привести людей к мысли, что файлам классов Java действительно нужна отдельная версия для каждой виртуальной машины, а не кроссплатформенность.
На самом деле я предпочитаю иметь отдельный переводчик байт-кода в собственный, который вы могли бы использовать для выполнения чего-то вроде этого заранее, создавая файлы классов, которые явно созданы для конкретной виртуальной машины, возможно, с исходным байт-кодом в них, чтобы вы также может работать с разными виртуальными машинами. Но это, вероятно, исходит из моего опыта: я в основном занимаюсь Java ME, и мне очень больно, что компилятор Java не умеет компилировать.
источник