Java JAXBContext 初始化加速?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/794354/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 19:34:54  来源:igfitidea点击:

JAXBContext initialization speedup?

javaperformancejaxb

提问by Hans-Peter St?rr

Is there any way to speed up the initialization of javax.xml.bind.JAXBContexts with a large (>1000) number of classes? In our XML heavy application the startup time is some 10 minutes and consists mainly of the initialization time of the JAXBContexts. :-(

有没有办法用大量(> 1000)个类来加速 javax.xml.bind.JAXBContexts 的初始化?在我们的 XML 繁重的应用程序中,启动时间大约为 10 分钟,主要包括 JAXBContexts 的初始化时间。:-(

We are using Sun's JAXB implementation in the JDK 1.5 and the org.jvnet.jaxb2.maven2.maven-jaxb2-plugin for the code generation from XSDs.

我们在 JDK 1.5 中使用 Sun 的 JAXB 实现,并使用 org.jvnet.jaxb2.maven2.maven-jaxb2-plugin 从 XSD 生成代码。

Clarification: The problem is not that we have many instances of a JAXBContext with the same contextpaths, but the problem is that the initialization of one single JAXBContext takes tens of seconds since it has to load and process thousands of classes. (Our XSDs are fairly large and complicated.) All JAXBContext instances have different contextpaths - we cannot reduce the number further.

澄清:问题不在于我们有许多具有相同上下文路径的 JAXBContext 实例,而是问题在于单个 JAXBContext 的初始化需要数十秒,因为它必须加载和处理数千个类。(我们的 XSD 相当大且复杂。)所有 JAXBContext 实例都有不同的上下文路径 - 我们无法进一步减少数量。

采纳答案by skaffman

The JAXB reference implementation has a sort-of-undocumented system property for exactly this reason:

正是由于这个原因,JAXB 参考实现具有某种未记录的系统属性:

-Dcom.sun.xml.internal.bind.v2.runtime.JAXBContextImpl.fastBoot=true

or for old versions prior to the package refactoring:

或者对于包重构之前的旧版本:

-Dcom.sun.xml.bind.v2.runtime.JAXBContextImpl.fastBoot=true

This instructs JAXB to skip the expensive process of pre-caching the various reflection muscles it needs to do the job. Instead, it will do all the reflection when the context gets used. This makes for a slower runtime, but considerably faster initialization, especially for large numbers of classes.

这指示 JAXB 跳过预先缓存它完成工作所需的各种反射肌肉的昂贵过程。相反,它会在使用上下文时进行所有反射。这会导致运行时间变慢,但初始化速度要快得多,尤其是对于大量类。

However, one part of the speed problem is unavoidable, and that's the fact that JAXB has to load every single one of your classes, and classloading is slow. This is apparent if you create a 2nd context immediately after the first, with the same configuration - you'll see it's much, much faster, having already loaded the classes.

然而,速度问题的一部分是不可避免的,这就是 JAXB 必须加载您的每一个类的事实,并且类加载很慢。如果您使用相同的配置在第一个上下文之后立即创建第二个上下文,这很明显 - 您会发现它已经加载了类,速度要快得多。

Also, you say that you have multiple JAXBContext instances because you have multiple contextpaths. Did you realise that you can put multiple context paths into a single context? You just need to pass them all as a semicolon-delimited string when you initialize the context, e.g.

此外,您说您有多个 JAXBContext 实例,因为您有多个上下文路径。您是否意识到可以将多个上下文路径放入单个上下文中?您只需要在初始化上下文时将它们全部作为分号分隔的字符串传递,例如

JaxbContext.newInstance("a.b.c:x.y.z");

will load the contexts a.b.cand x.y.z. It likely won't make any difference to performance, though.

将加载上下文a.b.cx.y.z. 不过,它可能不会对性能产生任何影响。

回答by StaxMan

In general, you should not have to create many instances of JAXBContext, as they are thread-safe after they have been configured. In most cases just a single context is fine.

通常,您不必创建许多 JAXBContext 实例,因为它们在配置后是线程安全的。在大多数情况下,只有一个上下文就可以了。

So is there specific reason why many instances are created? Perhaps there was assumption they are not thread-safe? (which is understandable given this is not clearly documented -- but it is a very common pattern, need syncing during configuration, but not during usage as long as config is not changed).

那么创建许多实例是否有特定原因?也许有人假设它们不是线程安全的?(这是可以理解的,因为没有明确记录 - 但它是一种非常常见的模式,需要在配置期间同步,但只要不更改配置,就不需要在使用期间同步)。

Other than this, if this is still a problem, profiling bottlenecks & filing an issue at jaxb.dev.java.net (pointing hot spots from profile) would help in getting things improved. JAXB team is very good, responsive, and if you can show where problems are they usually come up with good solutions.

除此之外,如果这仍然是一个问题,在 jaxb.dev.java.net 上分析瓶颈并提交问题(从配置文件中指出热点)将有助于改进事情。JAXB 团队非常优秀,反应迅速,如果您能指出问题出在哪里,他们通常会提出很好的解决方案。

回答by chetan

JAXBContext is indeed thread-safe, so wrapping it with a singleton is advised. I wrote a simple singleton containing a class->context map that seems to do the job. You may also want to create a pool of [un]marshaller objects if you're application uses many threads, as these objects are not thread-safe and you may see some initialization penalties with these as well.

JAXBContext 确实是线程安全的,因此建议用单例包装它。我写了一个简单的单例,其中包含一个似乎可以完成这项工作的类->上下文映射。如果您的应用程序使用多个线程,您可能还想创建一个 [un]marshaller 对象池,因为这些对象不是线程安全的,并且您可能会看到这些对象的一些初始化惩罚。

回答by Hans-Peter St?rr

In our case updating the JAXB libraries was a good idea. Incidentially, using the server VM instead of the client VM even in the development environment was a good idea here, even though it normally slows down server startup: since the JAXB initialization takes so much time the better compilation of the server VM helps.

在我们的例子中,更新 JAXB 库是一个好主意。顺便说一句,即使在开发环境中使用服务器 VM 而不是客户端 VM 在这里也是一个好主意,尽管它通常会减慢服务器启动速度:因为 JAXB 初始化需要很多时间,所以更好地编译服务器 VM 会有所帮助。