(1)我有一个资源密集型函数f,其调用导致大量内存分配。因为在f内部,将存在大量异议关系集合以构造到内存中。
(2)但是,在我的工作量中,我碰巧需要反复调用函数,例如在for循环和map函数中调用超过1K次。这样,调用f的循环会迅速关闭JVM。
for {
calling f here
}
Run Code Online (Sandbox Code Playgroud)
为了使上述工作负载正常工作,我在调用f之前引入Thread.sleep来引入间隔以延迟f调用的每次迭代,如下所示
for {
Thread.sleep (10)
calling f here
}
Run Code Online (Sandbox Code Playgroud)
这个经过时间的确会减少总内存使用量,以使工作量超过大型工作量。
(3)但是,有以下已知作用:(a)增加GC的频率,(b)增加总响应时间。因此,我需要根据客户端和服务器的超时配置进行调整。(c)延迟可以线性增长,当需要增加迭代时,延迟不会扩大。(d)如果有同时请求触发上述相同工作量的请求,则其他请求将超时。
我的问题:如何从字面上调用资源密集型功能:
(A)(2)以合理的响应时间同时处理上述一个大工作量的最佳方法是什么?(B)(2)同时处理多个大型工作负载的最佳方法是什么?
如果f不泄漏资源,那么在单个线程中调用它1000次将不会使jvm崩溃,因为在任何给定时间它只会为一个调用分配资源。
因此,我想您要么发生内存泄漏,要么从太多不同的线程调用它。既然Thread.sleep有帮助,我敢打赌第二。但这不是一个可靠的解决方案。
要限制并发调用的数量,f可以在专用上运行它ExecutionContext。
val ec = ExecutionContext.fromExecutor(Executors.newFixedThreadPool(10))
..
..
Future {
call f
}(ec)
Run Code Online (Sandbox Code Playgroud)
在的ec所有调用者之间共享实例f。
increase the frequency of GC这个问题通常无法解决:无论您如何安排执行时间,都必须收集您产生的所有垃圾。但是,如果程序必须具有较低的延迟,则可以稍微使用GC设置。如果有许多线程会产生大量短寿命垃圾,则您需要更多空间来存储新垃圾,而减少长寿命垃圾。它曾经XX:NewSize设置过,但是现代垃圾收集器的工作方式可能有所不同。
| 归档时间: |
|
| 查看次数: |
75 次 |
| 最近记录: |