nd4j 和 flink 内存泄漏

Cor*_*vus 5 java jvm javacpp apache-flink nd4j

使用 ND4J 和 Flink,我有一个处理函数,它接收 POJO,使用 linalg ndarray 使用一堆数学计算结果,并输出 pojo。当使用 Linux CPU 后端在集群上运行程序时,无论是否有 avx512,我都可以看到内存使用量只会上升。nd4j 计算的进程函数似乎存在内存泄漏。我没有在该方法之外保留任何引用,因此没有理由不释放内存 GC 被调用,但它不会释放太多内存。我也尝试过使用工作区功能,但它没有改变任何东西

我尝试过更改 GC、更改堆/堆外大小、设置 bytedeco 的 maxbytes 和 maxphysicalbytes、使用工作区,但没有任何帮助

小智 0

以下是我能想到的一些建议:

  1. 工作区:您提到您尝试使用工作区,但没有看到改进。工作区对于有效管理内存至关重要。确保您正确使用它。这是一个例子:
// Create a workspace
MemoryWorkspace workspace = Nd4j.getWorkspaceManager().getAndActivateWorkspace(WorkspaceConfiguration.builder().initialSize(1e6).overallocationLimit(0.1).policyLearning(LearningPolicy.FIRST_LOOP).build());

try {
    // Your ND4J calculations here
} finally {
    // Close the workspace
    workspace.close();
}
Run Code Online (Sandbox Code Playgroud)
  1. 释放资源:确保在不再需要内存时显式释放内存。在Flink中,使用ValueState.clear()ListState.clear()来释放状态相关的资源。

  2. 检查本机后端配置:根据您正在执行的具体计算,您可能需要配置 ND4J 本机后端以更好地满足您的需求。这可能涉及 CPU 和 GPU 后端之间的切换或微调本机后端设置。

    要配置原生后端,可以设置环境变量。例如:

     export ND4J_SYSTEM_PROP=cpu
     export ND4J_CPU_FEATURES=avx512
    
    Run Code Online (Sandbox Code Playgroud)

    根据您的系统的功能和要求进行相应调整。

  3. Flink Off-Heap State:如果您正在使用 Flink 的状态,如果您的状态较大,您可以检查 Flink 是否配置为使用堆外状态存储。堆外状态有助于减少 Flink 应用程序的内存占用。

如果没有什么对你有用:

考虑分析和监视:使用分析工具和监视来了解内存使用模式和潜在的内存泄漏。VisualVM、YourKit 或 Flink 的内置指标等工具可以帮助识别内存未按预期释放的区域。HTH。