При написании микробенчмарков можно наблюдать большую разницу во времени выполнения в зависимости от того, скомпилирован метод или нет. Есть ли способ узнать из программы, был ли скомпилирован конкретный метод? В качестве альтернативы, есть ли способ запросить его или узнать, как его адекватно разогреть без какой-либо дополнительной информации, например, о. флаги переданы JVM? Очевидно, что это не обязательно будет идеально (например, может присутствовать какое-то условие, которое заставляет JVM возвращаться к интерпретируемому коду), но это, безусловно, будет улучшением.
Есть ли способ узнать из JVM, был ли конкретный метод скомпилирован JIT?
Ответы (2)
Для Sun/Oracle JVM вы можете использовать настройку -XX:CompileThreshold=1000
.
Это, как указано в официальной документации, определяет :
Количество вызовов/ветвей метода перед компиляцией
Затем просто используйте номер, чтобы «разогреть» JVM.
Вы также можете использовать -XX:-PrintCompilation
вместе с -XX:CompileThreshold
, чтобы получать уведомления (в консоли) при компиляции метода.
Я почти уверен, что вы можете включить ведение журнала, которое покажет, когда методы JITCed. Но я не знаю, как изнутри Java это сказать.
И имейте в виду, что JIT-компиляция — это не событие, а процесс — метод может быть перекомпилирован несколько раз, когда становится доступной дополнительная информация о его характеристиках.
Наконец, обратите внимание, что «прогрев» в общем случае сомнительный. Хотя обычно вы можете надежно «разогреть» один метод, это намного сложнее даже с умеренно большим приложением из-за ряда факторов.
(Хотя я не знаю ни одной причины, по которой возможность чтения какого-либо статуса JITC для метода нельзя было добавить во встроенные инструменты отладки.)
Добавлено: Одна вещь, о которой следует помнить при сравнительном анализе "фрагментов" кода, заключается в том, что самый внешний метод, выполняющий весь цикл, часто не поддерживает JITC (в зависимости от того, как реализован JITC) из-за к тому факту, что он никогда не возвращается и, следовательно, версия JITCed никогда не может быть вызвана. Таким образом, всегда следует помещать «мясо» кода, подлежащего тестированию, в отдельный метод, который вызывается повторно, а не помещать цикл и код, подлежащий тестированию, в один и тот же метод.