Ich benutze Spark Standalone Einzelmaschine, mit 128G Speicher und 32 Kernen. Die folgenden sind Einstellungen, die ich denke, relevant für mein Problem:Spark-Anwendung - Java.lang.OutOfMemoryError: Java-Heap-Raum
spark.storage.memoryFraction 0.35
spark.default.parallelism 50
spark.sql.shuffle.partitions 50
Ich habe eine Spark-Anwendung, in der es eine Schleife für 1000 Geräte ist. Mit jeder Schleife (Gerät) bereitet sie einen Merkmalsvektor vor und ruft dann k-Means von MLLib auf. Bei der 25. bis 30. Iteration der Schleife (Verarbeitung des 25. bis 30. Geräts) tritt der Fehler "Java.lang.OutOfMemoryError: Java-Heap-Speicher" auf.
Ich versuchte MemoryFraction von 0,7 bis 0,35, aber es hat nicht geholfen. Ich habe auch Parallelismus/Partitionen zu 200 ohne Glück versucht. Die JVM-Option lautet "-Xms25G -Xmx25G -XX: MaxPermSize = 512m". Meine Datengröße beträgt nur etwa 2G.
Hier Stack-Trace ist:
java.lang.OutOfMemoryError: Java heap space
at java.util.Arrays.copyOf(Arrays.java:2271)
at java.io.ByteArrayOutputStream.grow(ByteArrayOutputStream.java:118)
at java.io.ByteArrayOutputStream.ensureCapacity(ByteArrayOutputStream.java:93)
at java.io.ByteArrayOutputStream.write(ByteArrayOutputStream.java:153)
at java.io.ObjectOutputStream$BlockDataOutputStream.write(ObjectOutputStream.java:1841)
at java.io.ObjectOutputStream.defaultWriteFields(ObjectOutputStream.java:1533)
at java.io.ObjectOutputStream.writeSerialData(ObjectOutputStream.java:1508)
at java.io.ObjectOutputStream.writeOrdinaryObject(ObjectOutputStream.java:1431)
at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1177)
at java.io.ObjectOutputStream.writeObject(ObjectOutputStream.java:347)
at scala.collection.mutable.HashMap$$anonfun$writeObject$1.apply(HashMap.scala:138)
at scala.collection.mutable.HashMap$$anonfun$writeObject$1.apply(HashMap.scala:136)
at scala.collection.mutable.HashTable$class.foreachEntry(HashTable.scala:230)
at scala.collection.mutable.HashMap.foreachEntry(HashMap.scala:40)
at scala.collection.mutable.HashTable$class.serializeTo(HashTable.scala:125)
at scala.collection.mutable.HashMap.serializeTo(HashMap.scala:40)
at scala.collection.mutable.HashMap.writeObject(HashMap.scala:136)
at sun.reflect.GeneratedMethodAccessor116.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
at java.io.ObjectStreamClass.invokeWriteObject(ObjectStreamClass.java:988)
at java.io.ObjectOutputStream.writeSerialData(ObjectOutputStream.java:1495)
at java.io.ObjectOutputStream.writeOrdinaryObject(ObjectOutputStream.java:1431)
at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1177)
at java.io.ObjectOutputStream.defaultWriteFields(ObjectOutputStream.java:1547)
at java.io.ObjectOutputStream.writeSerialData(ObjectOutputStream.java:1508)
at java.io.ObjectOutputStream.writeOrdinaryObject(ObjectOutputStream.java:1431)
at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1177)
at java.io.ObjectOutputStream.defaultWriteFields(ObjectOutputStream.java:1547)
at java.io.ObjectOutputStream.writeSerialData(ObjectOutputStream.java:1508)
at java.io.ObjectOutputStream.writeOrdinaryObject(ObjectOutputStream.java:1431)
at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1177)
Zu Beginn sieht die Anwendung in Ordnung, aber nachdem er eine Zeit lang und Prozesse immer mehr Geräte läuft, wird Java Heap besetzt allmählich und Speicher freigegeben wird nicht durch JVM. Wie kann man ein solches Problem diagnostizieren und beheben?
Es versucht, so Daten zu serialisieren, möglicherweise eine sehr große Datenmenge. Ich schlage vor, dass Sie die maximale Heap-Größe auf 100 GB anstelle von 25 GB erhöhen. –
Probehaufen Größe 100G jetzt. Danke für den Vorschlag. – wdz
Haben Sie versucht, spark.rdd.compress auf true zu setzen? –