OutOfMemoryError: GC overhead grænse overskredet

1. Oversigt

Kort sagt, JVM sørger for at frigøre hukommelse, når objekter ikke længere bruges; denne proces kaldes Garbage Collection (GC).

Det GC-overheadgrænse overskredet fejl er en fra familien af java.lang.OutOfMemoryError og er en indikation af en ressource (hukommelse) udmattelse.

I denne hurtige artikel vil vi se på, hvad der forårsager java.lang.OutOfMemoryError: GC overhead grænse overskredet fejl, og hvordan det kan løses.

2. GC overhead grænse overskredet fejl

OutOfMemoryError er en underklasse af java.lang.VirtualMachineError; det kastes af JVM, når det støder på et problem relateret til udnyttelse af ressourcer. Mere specifikt, fejlen opstår, når JVM'en brugte for meget tid på at udføre affaldssamling og var kun i stand til at genvinde meget lidt bunkeplads.

Ifølge Java-dokumenter er JVM som standard konfigureret til at kaste denne fejl, hvis Java-processen bruger mere end 98% af sin tid på at lave GC, og når kun mindre end 2% af bunken gendannes i hver kørsel. Med andre ord betyder det, at vores ansøgning har opbrugt næsten al den tilgængelige hukommelse, og Garbage Collector har brugt for meget tid på at rense den og mislykkedes gentagne gange.

I denne situation oplever brugerne ekstrem langsomhed i applikationen. Visse operationer, som normalt gennemføres i millisekunder, tager længere tid at gennemføre. Dette skyldes, at CPU'en bruger hele sin kapacitet til affaldssamling og derfor ikke kan udføre andre opgaver.

3. Fejl i aktion

Lad os se på et stykke kode, der kaster java.lang.OutOfMemoryError: GC overhead grænse overskredet.

Vi kan opnå det for eksempel ved at tilføje nøgleværdipar i en ubestemt løkke:

offentlig klasse OutOfMemoryGCLimitExceed {public static void addRandomDataToMap () {Map dataMap = new HashMap (); Tilfældig r = ny tilfældig (); while (true) {dataMap.put (r.nextInt (), String.valueOf (r.nextInt ())); }}}

Når denne metode påberåbes, med JVM-argumenterne som -Xmx100m -XX: + UseParallelGC (Java bunke størrelse er indstillet til 100MB og GC algoritme er ParallelGC), vi får en java.lang.OutOfMemoryError: GC overhead grænse overskredet fejl. For at få en bedre forståelse af forskellige Garbage Collection-algoritmer kan vi tjekke Oracle's Java Garbage Collection Basics tutorial.

Vi får en java.lang.OutOfMemoryError: GC overhead grænse overskredet fejl meget hurtigt ved at køre følgende kommando fra projektets rod:

mvn exec: exec

Det skal også bemærkes, at vi i nogle situationer muligvis støder på en bunkepladsfejl, før vi støder på GC-overheadgrænse overskredet fejl.

4. Løsning af GC overhead grænse overskredet fejl

Den ideelle løsning er at finde det underliggende problem med applikationen ved at undersøge koden for eventuelle hukommelseslækager.

Følgende spørgsmål skal behandles:

  • Hvad er objekterne i applikationen, der optager store dele af bunken?
  • I hvilke dele af kildekoden tildeles disse objekter?

Vi kan også bruge automatiserede grafiske værktøjer som JConsole, som hjælper med at opdage ydelsesproblemer i koden inklusive java.lang.OutOfMemoryErrors.

Den sidste udvej ville være at øge dyngestørrelsen ved at ændre JVM-startkonfigurationen. For eksempel giver dette 1 GB bunkeplads til Java-applikationen:

java -Xmx1024m com.xyz.TheClassName

Dette løser dog ikke problemet, hvis der er hukommelseslækager i den aktuelle applikationskode. I stedet udsætter vi bare fejlen. Derfor er det mere tilrådeligt at revurdere applikationens hukommelsesforbrug grundigt.

5. Konklusion

I denne vejledning undersøgte vi java.lang.OutOfMemoryError: GC overhead grænse overskredet og årsagerne bag det.

Som altid kan kildekoden relateret til denne artikel findes på GitHub.