3

最近成功创建了一个自定义顶点类,其中每个顶点都有一个LongWritable id,这个id也是它自己的值。我的 Giraph 程序在一个小的顶点集(100,000 个顶点)上成功运行,程序完成并输出预期值。但是,当我将卷增加到 3000 万个顶点时,程序会在总内存用完时挂起(每个映射器的堆大小为 1.5 GB)。由于我的顶点类只包含一个 id 和值(8 + 8 = 16 字节)以及发出的边(平均 8*8*2 = 128 字节),我不明白为什么内存消耗如此之高。从下面的日志消息中可以看出,内存在 1363 MB 处最大为 450 万个顶点,因此当 Giraph 运行时每个顶点占用 317 个字节。Giraph 中有哪些额外的数据结构导致字节/顶点如此之高?

readVertexInputSplit: Loaded 4500000 vertices at 90245.3768041096 vertices/sec 0 edges at 0.0 edges/sec Memory (free/total/max) = 187.52M / 1363.00M / 1365.50M

waitFor: Future result not ready yet java.util.concurrent.FutureTask@5f7bd943

4

1 回答 1

0

只是为任何寻找答案的人提供答案。

尝试改变 Giraph 保存分区的方式。如果使用默认值,则会产生很大的开销。改用org.apache.giraph.partition.ByteArrayPartition它,它只有效地将您的数据保存为字节数组,而不是包装形式。Java 有保存对象的开销,这在您的情况下非常明显,因为您有许多小对象 - 因此浪费也很高。

此外,通常建议运行小型映射器。最好有几个强大的节点(大约 10 个内核和 30-60GB RAM)而不是几十个小节点。

可能还有很多其他原因,但我不能说没有细节。

于 2019-10-23T18:10:06.997 回答