多个JVM进程可以共享公共类的内存吗?

我想在我的Web服务器上运行多个Java进程,每个Web应用程序一个。 我正在使用一个Web框架(Play),它有很多支持类和jar文件,Java进程使用大量内存。 One Play过程显示大约225MB的“驻留私人”内存。 (我在Mac OS X上使用Java 1.7.0_05进行测试。)特定于应用程序的代码可能只有几MB。 我知道典型的Java Web应用程序是添加到一个服务器进程(Tomcat等)的jar,但看起来运行Play的标准方法是作为独立的应用程序/进程。 如果这些是C程序,那么200MB的大部分将是共享库,而不是在每个应用程序中重复。 有没有办法在Java中实现这一点? 我看到一些关于类数据共享的页面,但这似乎只适用于核心运行时类。

此时并且使用Oracle VM,这是不可能的。

但我同意,这将是一个很好的function,特别是因为Java拥有它需要自动完成的所有信息。

在我的帽子中,我认为JIT是其无法工作的唯一原因:JIT将运行时行为考虑在内。 因此,如果应用程序A使用与应用程序B不同的模式中的某些代码,则会导致在运行时生成不同的汇编程序代码。

但是,通常的“模式”是“这个代码的使用频率”。 因此,如果应用A经常调用某种方法而B没有,它们仍然可以共享代码,因为A已经为优化/编译它付出了代价。

您可以尝试将多个应用程序作为WAR文件部署到单个VM中。 但根据我的经验,这通常会导致代码无法正确清理线程本地或关闭钩子的问题。

IBM JDK有一个jvm参数来实现这一目标。 查看@ http://www.ibm.com/developerworks/library/j-sharedclasses/

这将进入下一步: http : //www.ibm.com/developerworks/library/j-multitenant-java/index.html

如果您正在使用支持虚拟主机的servlet容器(我相信Tomcat 会这样做 ),您将能够使用play2-war-plugin 。 从Play 2.1开始,永远是root应用程序的要求将被取消,因此您可能可以使用任何servlet容器。

如果您可能需要调整war文件以将内容从WEB-INF/lib到servlet容器的lib目录,以避免再次加载所有类,这可能会影响您的应用程序,如果它使用单例或其他forms的类共享数据。

在JVM实例之间共享内存的问题在移动平台上更加紧迫,据我所知,Android在Zygote中有一个非常聪明的解决方案:虚拟机已初始化,然后在运行应用程序时,它是fork() ed。 Linux在RAM页面上使用copy-on-write,因此大多数数据都不会重复。

如果你在Linux上运行并且想尝试使用Dalvik作为你的VM(我看到声称在Dalvik上有一个tomcat的工作端口),那么移植这个解决方案是可能的。 我希望这是一项大量的工作,最终在内存升级上节省了几美元。