Vra

Ek skryf'n kliënt-kant Swaai aansoek (grafiese font ontwerper) op Java 5.Onlangs, ek hardloop in java.lang.OutOfMemoryError: Java heap space fout, want ek is nie die feit dat konserwatiewe op geheue gebruik.Die gebruiker kan maak onbeperkte aantal lêers, en die program hou die oop voorwerpe in die geheue.Na'n vinnige navorsing het ek gevind Ergonomie in die 5.0 Java Virtuele Masjien en die ander sê: op Windows masjien die JVM standaard max hoop grootte as 64MB.

Gegewe hierdie situasie, hoe moet ek gaan met hierdie beperking?

Ek kan verhoog die max hoop grootte met behulp van die opdrag lyn opsie om te java, maar wat sou vereis dat die uitzoeken beskikbaar RAM en die skryf van'n paar bekendstelling van program of script.Naas, die verhoging van om'n paar eindige max nie uiteindelik ontslae te raak van die probleem.

Ek kon herskryf sommige van my kode te volhard voorwerpe te lêer stelsel gereeld (met behulp van'n databasis is die dieselfde ding) vry te maak van die geheue.Dit kan werk, maar dit is waarskynlik'n baie werk ook.

As jy nie kan wys my die besonderhede van bogenoemde idees of'n alternatiewe soos outomatiese virtuele geheue, die uitbreiding van hoop grootte dinamiese, wat sal groot wees.

Was dit nuttig?

Oplossing

Uiteindelik het jy altyd'n eindige max van hoop te gebruik nie saak wat platform wat jy loop op.In Windows 32 bietjie hierdie is rondom 2GB (nie spesifiek hoop maar die totale bedrag van die geheue per proses).Dit gebeur net dat Java kies om te maak van die standaard kleiner (vermoedelik sodat die programmeerder kan nie die skep van programme wat weghol geheue toekenning sonder om te loop in hierdie probleem en om te ondersoek presies wat hulle doen).

So dit gegee is daar verskeie benaderings wat jy kan neem om óf te bepaal wat die bedrag van die geheue wat jy nodig het, of te verminder die bedrag van die geheue wat jy gebruik.Een algemene fout met vullis versamel tale soos Java of C# is om te hou om verwysings na voorwerpe wat jy geen meer is die gebruik van, of die toekenning van baie voorwerpe as jy kan onthou hulle plaas.So lank as voorwerpe het'n verwysing na hulle, hulle sal voortgaan om te gebruik hoop ruimte as die vullis versamelaar sal nie verwyder.

In hierdie geval kan jy'n Java geheue profiler om te bepaal watter metodes in jou program is die toekenning van'n groot aantal van die voorwerpe en dan bepaal of daar is'n manier om seker te maak hulle word nie meer verwys, of om nie ken hulle in die eerste plek.Een opsie wat ek het in die verlede gebruik is "JMP" http://www.khelekore.org/jmp/.

As jy bepaal wat jy is die toekenning van hierdie voorwerpe vir'n rede en wat jy nodig het om te hou rondom verwysings (afhangende van wat jy doen dit dalk die geval is), sal jy net nodig het om te verhoog die max hoop grootte wanneer jy begin die program.Egter, sodra jy dit doen die geheue profilering en verstaan hoe jou voorwerpe is om toegeken moet jy'n beter idee oor hoeveel geheue wat jy nodig het.

In die algemeen, as jy kan nie waarborg dat jou program sal loop in'n paar beperkte bedrag van die geheue (miskien afhangende van insette grootte) sal jy altyd loop in hierdie probleem.Net na die uitputting van al hierdie, sal jy nodig het om te kyk in die kas voorwerpe uit te skyf, ens.Op hierdie punt wat jy moet'n baie goeie rede om te sê "ek moet Xgb van die geheue" vir iets en jy kan nie werk om dit deur die verbetering van jou algoritmes of geheue toekenning patrone.Oor die algemeen dit sal slegs gewoonlik die geval is vir die algoritmes wat op groot datastelle (soos'n databasis of'n wetenskaplike analise program) en dan tegnieke soos caching en geheue gekarteer IO geword nuttig.

Ander wenke

Run Java met die opdrag-lyn opsie -Xmx, wat die maksimum stel grootte van die wal.

Sien hier vir meer inligting .

Jy kan spesifiseer per projek hoeveel hoop ruimte jou projek wil

Die volgende is vir Eclipse Helios / Juno / Kepler :

Right kliek op

 Run As - Run Configuration - Arguments - Vm Arguments, 

dan dié byvoeging

-Xmx2048m

Die verhoging van die hoop grootte is nie 'n "fix" dit is 'n "pleister", 100% tydelike. Dit sal weer crash in 'n ander plek. Om hierdie probleme te voorkom, skryf 'n hoë werkverrigting kode.

  1. Gebruik plaaslike veranderlikes waar moontlik.
  2. Maak seker dat jy die korrekte voorwerp te kies (EX: Seleksie tussen String, StringBuffer en StringBuilder)
  3. Gebruik 'n goeie kode stelsel vir jou program (EX: Die gebruik van statiese veranderlikes VS nie staties veranderlikes)
  4. Ander dinge wat kan werk op jou kode.
  5. Probeer om te beweeg met Multy threading

Big caveat ---- by my kantoor, ons vind dat (op sommige vensters masjiene) ons kan nie meer as 512m vir Java hoop toeken. Dit blyk te danke aan die Kaspersky Anti-Virus produk op 'n paar van dié masjiene geïnstalleer te wees. Na die verwydering van daardie AV produk, het ons gevind ons kan ten minste 1.6gb, d.w.z, -Xmx1600m toewys (m is verpligtend ander wyse dit sal lei tot 'n ander fout "Te klein aanvanklike hoop") werk.

Geen idee as dit gebeur met ander AV produkte, maar vermoedelik dit gebeur omdat die AV program is reservering van 'n klein blok van geheue in elke adres ruimte, waardeur 'n enkele regtig groot toekenning voorkoming.

VM argumente gewerk vir my in verduistering. As jy met behulp van verduistering weergawe 3.4, doen die volgende

gaan na Run --> Run Configurations --> kies dan die projek onder Maven bou -> kies dan die blad "JRE" -.> Gee dan -Xmx1024m

As alternatief wat jy kan doen Run --> Run Configurations --> select the "JRE" tab --> gee dan -Xmx1024m

Dit moet die geheue hoop vir al die bou / projekte te verhoog. Bogenoemde geheue grootte is 1 GB. Jy kan die manier waarop jy wil te optimaliseer.

Ja, met -Xmx jy kan meer geheue instel vir jou JVM. Om seker te wees dat jy nie lek of geheue afval. Neem 'n hoop stort en gebruik die Eclipse Memory Analyzer te analiseer jou geheue verbruik.

Ek wil graag by te voeg aanbevelings van oracle die moeilikheid skiet artikel.

Uitsondering in die draad thread_name: java.lang.OutOfMemoryError:Java hoop ruimte

Die detail boodskap Java hoop ruimte dui voorwerp kan nie toegeken word in die Java hoop.Hierdie fout impliseer nie noodwendig'n geheue lek

Moontlike oorsake:

  1. Eenvoudige opset kwessie, waar die gespesifiseerde hoop grootte is onvoldoende vir die aansoek.

  2. Aansoek is onbedoeld hou verwysings na voorwerpe, en dit verhoed dat die voorwerpe van vullis versamel.

  3. Die oormatige gebruik van finalizers.

Een ander potensiële bron van hierdie fout ontstaan met aansoeke wat maak dat die oormatige gebruik van finalizers.As'n klas het'n finaliseer metode, dan voorwerpe van daardie tipe nie hul ruimte teruggeëis op vullisverwydering tyd

Na vullisverwydering, die voorwerpe is tougestaan vir finalisering, wat voorkom op'n later tyd. finalizers uitgevoer word deur'n daemon draad wat die dienste van die finalisering tou.As die finalizer draad kan nie tred hou met die finalisering ry, dan is die Java hoop kon vul en hierdie tipe van OutOfMemoryError uitsondering sou gegooi word.

Een scenario wat kan veroorsaak hierdie situasie is wanneer'n aansoek skep 'n hoë prioriteit drade wat veroorsaak dat die finalisering tou te verhoog teen'n koers wat is vinniger as die tempo waarteen die finalizer draad is die diens wat tou.

Volg hierdie stappe:

  1. Open catalina.sh van tomcat / bin.

  2. Verandering JAVA_OPTS om

    JAVA_OPTS="-Djava.awt.headless=true -Dfile.encoding=UTF-8 -server -Xms1536m 
    -Xmx1536m -XX:NewSize=256m -XX:MaxNewSize=256m -XX:PermSize=256m 
    -XX:MaxPermSize=256m -XX:+DisableExplicitGC"
    
  3. Start jou tomcat

maklike manier om OutOfMemoryError in Java te los, is om die maksimum hoop grootte te verhoog deur die gebruik van JVM opsies -Xmx512M, dit sal dadelik jou OutOfMemoryError op te los. Dit is my voorkeur oplossing wanneer ek OutOfMemoryError in Eclipse, Maven of ANT, terwyl die bou projek omdat gebaseer op grootte van die projek wat jy kan maklik 'n tekort aan Memory.

Hier is 'n voorbeeld van die verhoging van die maksimum hoop grootte van JVM, ook sy beter om -Xmx hou om rantsoen -Xms óf 1: 1 of 1:. 1.5 as jy die opstel van hoop grootte in jou Java program

export JVM_ARGS="-Xms1024m -Xmx1024m"

Verwysing Link

Deur verstek vir ontwikkeling JVM gebruik klein grootte en klein config vir ander prestasie-verwante funksies. Maar vir die produksie wat jy kan inskakel bv (Behalwe dit Aansoek Server spesifieke config kan bestaan) -> (As daar nog nie genoeg geheue om die versoek te voldoen en die hoop het reeds die maksimum grootte bereik, sal 'n OutOfMemoryError voorkom)

-Xms<size>        set initial Java heap size
-Xmx<size>        set maximum Java heap size
-Xss<size>        set java thread stack size

-XX:ParallelGCThreads=8
-XX:+CMSClassUnloadingEnabled
-XX:InitiatingHeapOccupancyPercent=70
-XX:+UnlockDiagnosticVMOptions
-XX:+UseConcMarkSweepGC
-Xms512m
-Xmx8192m
-XX:MaxPermSize=256m (in java 8 optional)

Byvoorbeeld: Op Linux-platform vir die produksie af verkieslik instellings.

Na die aflaai en die instel van bediener met hierdie manier http://www.ehowstuff.com/how-to-install-and-setup-apache-tomcat-8-on-centos-7-1-rhel-7/

1.Create setenv.sh lêer op die gids / opt / Tomcat / bin /

   touch /opt/tomcat/bin/setenv.sh

2.Open en skryf hierdie params vir die opstel van beter af.

nano  /opt/tomcat/bin/setenv.sh 

export CATALINA_OPTS="$CATALINA_OPTS -XX:ParallelGCThreads=8"
export CATALINA_OPTS="$CATALINA_OPTS -XX:+CMSClassUnloadingEnabled"
export CATALINA_OPTS="$CATALINA_OPTS -XX:InitiatingHeapOccupancyPercent=70"
export CATALINA_OPTS="$CATALINA_OPTS -XX:+UnlockDiagnosticVMOptions"
export CATALINA_OPTS="$CATALINA_OPTS -XX:+UseConcMarkSweepGC"
export CATALINA_OPTS="$CATALINA_OPTS -Xms512m"
export CATALINA_OPTS="$CATALINA_OPTS -Xmx8192m"
export CATALINA_OPTS="$CATALINA_OPTS -XX:MaxMetaspaceSize=256M"

3.service tomcat restart

  

Let daarop dat die JVM gebruik meer geheue as net die hoop. Byvoorbeeld   Java metodes, draad stapels en inheemse handvatsels word toegeken in die geheue   skei van die hoop, asook JVM interne datastrukture.

Ek het dieselfde probleem gekonfronteer uit java hoop grootte.

Ek het twee oplossings as jy 'java 5 (1.5).

  1. net installeer jdk1.6 en gaan na die voorkeure van verduistering en stel die jre pad van jav1 1.6 as jy geïnstalleer het.

  2. Gaan jou VM argument dat dit 'wat dit ookal is. voeg net een lyn hieronder van al die argumente wat in VM argumente as -Xms512m -Xmx512m xx lees:. MaxPermSize = ... m (192m)

Ek dink dit sal werk ...

Ek iewers anders wat jy kan probeer lees - vang java.lang.OutOfMemoryError en op die vangs blok, kan jy al die hulpbronne wat jy ken dalk 'n baie geheue, nou bande gebruik en so meer, dan doen 'n System.gc() dan bevry weer probeer alles wat jy gaan doen.

Nog 'n manier is dit alhoewel, ek weet nie of dit sal werk, maar ek is tans die toets of dit sal werk op my aansoek.

Die idee is om vullisverwydering doen deur te bel System.gc () wat bekend is om vry geheue te verhoog. Jy kan hou die nagaan van hierdie na 'n geheue sluk kode voer.

//Mimimum acceptable free memory you think your app needs
long minRunningMemory = (1024*1024);

Runtime runtime = Runtime.getRuntime();

if(runtime.freeMemory()<minRunningMemory)
 System.gc();

As jy nodig het om te monitor jou geheue gebruik by runtime, die java.lang.management die pakket bied MBeans wat gebruik kan word om te monitor die geheue poele in jou VM (bv., eden ruimte, selfstandig geslag, ens), en ook vullisverwydering gedrag.

Die gratis hoop ruimte gerapporteer deur hierdie MBeans sal wissel baie, afhangende van GC gedrag, veral as jou aansoek genereer'n baie van die voorwerpe wat later GC-ed.Een moontlike benadering is om te monitor die gratis hoop spasie na elke volle-GC, wat jy kan in staat wees om te gebruik om'n besluit te maak op bevry geheue deur te volhard voorwerpe.

Uiteindelik, jou beste bet is om te beperk jou geheue retensie so ver as moontlik, terwyl die prestasie steeds aanvaarbaar.As'n vorige kommentaar opgemerk, die geheue is altyd beperk, maar jou inligting moet'n strategie vir die hantering van die geheue uitputting.

Let daarop dat as jy dit in 'n ontplooiing situasie nodig het, oorweeg die gebruik van Java Webstart (met 'n "ondisk" weergawe, nie die netwerk een - moontlik in Java 6u10 en later) as dit laat jou toe om die verskillende argumente spesifiseer om die JVM in 'n kruis platform manier.

Anders sal jy 'n bedryfstelsel spesifieke lanseerder wat die argumente wat jy nodig het stel nodig.

As hierdie kwessie gebeur in Wildfly 8 en JDK1.8, dan moet ons MaxMetaSpace instellings plaas spesifiseer van PermGen instellings.

Byvoorbeeld moet ons voeg hieronder opset in setenv.sh lêer van wildfly. JAVA_OPTS="$JAVA_OPTS -XX:MaxMetaspaceSize=256M"

Vir meer inligting, kyk Wildfly Heap Uitgawe

Met betrekking tot by NetBeans, kan jy maksimum hoop grootte om die probleem op te los ingestel.

Gaan na 'Run ", dan ->' Stel Projek Configuration" -> "Aanpassing '->' doen 'van sy opgeduik venster ->' VM Opsie '-> in' -Xms2048m vul -Xmx2048m.

As jy hou op die toekenning van & hou verwysings om beswaar, sal jy vul 'n bedrag van geheue wat jy het.

Een opsie is om 'n deursigtige lêer naby & oop wanneer hulle oortjies skakel (jy net 'n wyser te hou om die lêer te doen, en wanneer die gebruiker blad, jy naby & al die voorwerpe skoon skakel ... dit sal die maak lêer verander stadiger ... maar ...), en miskien hou net 3 of 4 lêers op geheue.

Ander ding wat jy moet doen is, wanneer die gebruiker 'n lêer oopmaak, laai dit, en onderskep enige OutOfMemoryError, dan (as dit nie moontlik is om die lêer oop te maak) sluit die lêer, sy oogmerke skoon te maak en te waarsku die gebruiker wat hy moet ongebruikte lêers te sluit.

Jou idee van dinamiese uitbreiding van virtuele geheue nie die probleem op te los, vir die masjien is beperk op hulpbronne, sodat jy moet versigtig wees en hanteer geheue probleme (of ten minste, wees versigtig met hulle).

'n Paar wenke i gesien met geheue lekkasies is:

-> Hou op gedagte dat indien jy iets het in 'n versameling en daarna vergeet, jy nog steeds 'n sterk verwysing na dit, so tot niet die versameling, skoon dit of iets te doen met dit ... as jy nie sal 'n geheugenlek moeilik om te vind.

-> Miskien, met behulp van versamelings met swak verwysings (weakhashmap ...) kan help met geheue probleme, maar jy sterk <> moet wees versigtig met dit, want jy mag vind dat die item wat jy kyk vir is ingesamel.

-> Nog 'n idee wat ek gevind het is om 'n aanhoudende versameling wat gestoor word op die databasis voorwerpe minste gebruik en deursigtig gelaai ontwikkel. Dit sou waarskynlik die beste benadering wees ...

Gelisensieer onder: CC-BY-SA met toeskrywing
Nie verbonde aan StackOverflow
scroll top