Можно ли предварительно загрузить JVM, чтобы ускорить запуск небольших одноразовых java-приложений?

2486
Vi.

Ожидаемый алгоритм:

  1. Вы запускаете JVM без реального приложения (только говорит ему загрузить несколько jar-файлов), он загружает и прослушивает сокет и ждет в фоновом режиме.
  2. Когда вы запускаете приложение ( preloaded_java -cp /usr/share/java/....jar:. qqq.jar), оно подключается к существующей загруженной JVM, загружает дополнительные jar-файлы (если есть) и выполняет основной класс.
  3. preloaded_java просто маршрутизирует ввод и вывод, обрабатывает прерывания и т. д.

Обновление Реализовано подтверждение концепции: http://vi-server.org/vi/code/prejvm/

$ clojure prejvm.clj& [1] 2883 $ nc 127.0.0.1 7711 <<< '{"mainclass" "test.Hello"}' $ nc 127.0.0.1 7712 java.lang.ClassNotFoundException: test.Hello at java.net.URLClassLoader$1.run(URLClassLoader.java:200) ... at clojure.main.main(main.java:37)  $ nc 127.0.0.1 7711 <<< '{"classpaths" ["file:///home/vi/code/prejvm/"], "mainclass" "test.Hello"}'  $ nc 127.0.0.1 7712 Hello, world; number of args is 0 qwe q e32e qda qwe q e32e qda  $ nc 127.0.0.1 7711 <<< '{"classpaths" ["file:///home/vi/code/prejvm/"], "mainclass" "test.Hello", "argv" ["qqq" "www" "eee"]}' $ nc 127.0.0.1 7712  Hello, world; number of args is 3 sdfasdfasf df sad sdfasdfasf df sad 

Обновление 2 : нашел ответ сам: сервер Nailgun (от VimClojure).

7

3 ответа на вопрос

3
Vi.

Используйте сервер Nailgun:

Начни это:

java -classpath /usr/share/java/clojure.jar:/usr/share/java/clojure-contrib.jar com.martiansoftware.nailgun.NGServer 127.0.0.1 

Используй это:

$ ng clojure.main  Clojure 1.2.0 user=>  $ ng test.Hello sdf sdf sdf Hello, world; number of args is 3 sdfsdf sdfsdf 

Его можно получить с помощью VimClojure: http://www.vim.org/scripts/script.php?script_id=2501

Быстрое прочтение не выявляет никаких трюков с загрузчиком классов, поэтому класс будет инициализирован только один раз за запуск сервера, а не "за использование". Это может или не может повлиять на правильность того, что вы используете под NailGun. Ken 14 лет назад 0
Если какой-то код не работает на NailGun из-за этого, то, вероятно, он написан плохо. В хорошей программе «инициализируется один раз за запуск сервера» должно означать, что это будет еще быстрее. Vi. 14 лет назад 0
0
sleske

Нет, то, что вы описываете, невозможно, по крайней мере, с Sun JVM, просто потому, что оно не реализовано (хотя это хорошая идея).

Однако, если вы просто запустите приложение один раз, ОС будет кэшировать данные в ОЗУ, которое было загружено с диска, поэтому последующие запуски должны быть намного быстрее. Это может уже помочь.

Если вам нужно более быстрое ускорение: можете ли вы изменить приложение, чтобы оно просто продолжало работать и принимало новый ввод?

Я хочу более-менее универсальный подход. Похоже, самой сложной частью для этого будет «псевдо-Java Runner», который читает аргументы и подключается к Java-демону. Vi. 14 лет назад 0
«... невозможно, по крайней мере, с Sun JVM» Почему это не может быть стороннее приложение? Все необходимые функции уже есть в JVM: наше приложение может как-то загружать класс и выполнять main (перенаправляя System. ). Vi. 14 лет назад 0
Странно, что Sun (/ Oracle) этого не делает, поскольку это было функцией нескольких "серверных" JVM с 1998 года или около того. Daniel R Hicks 10 лет назад 0
0
jlliagre

Конечно, это может быть сделано. То, что вы описываете, на самом деле очень близко к тому, как работает сервер приложений Java EE.

Так что он должен быть как сервер приложений Java для консольных программ. Vi. 14 лет назад 0

Похожие вопросы