Cosa sono Runtime.getRuntime (). TotalMemory () e freeMemory ()?

Mi sono chiesto quale sia il significato esatto di Runtime.getRuntime (). TotalMemory () , Runtime.getRuntime (). FreeMemory () e Runtime.getRuntime (). MaxMemory () è.

La mia comprensione è, Runtime.getRuntime().totalMemory() restituisce la memoria totale utilizzata dal mio processo. È corretto?

Che ne dici di freeMemory() e maxMemory() ?

Secondo l’ API

 totalMemory() 

Restituisce la quantità totale di memoria nella Java virtual machine. Il valore restituito da questo metodo può variare nel tempo, a seconda dell’ambiente host. Si noti che la quantità di memoria richiesta per contenere un object di un determinato tipo può dipendere dall’implementazione.

 maxMemory() 

Restituisce la quantità massima di memoria che la macchina virtuale Java tenterà di utilizzare. Se non esiste un limite inerente, verrà restituito il valore Long.MAX_VALUE.

 freeMemory() 

Restituisce la quantità di memoria disponibile nella Java Virtual Machine. Chiamare il metodo gc potrebbe aumentare il valore restituito da freeMemory.

In riferimento alla tua domanda, maxMemory() restituisce il valore -Xmx .

Forse ti starai chiedendo perché esiste un totaleMemory () AND un maxMemory () . La risposta è che la JVM alloca pigramente la memoria. Diciamo che inizi il tuo processo Java come tale:

 java -Xms64m -Xmx1024m Foo 

Il processo inizia con 64 MB di memoria e, se e quando ha bisogno di più (fino a 1024 m), allocherà memoria. totalMemory() corrisponde alla quantità di memoria attualmente disponibile per JVM per Foo. Se la JVM ha bisogno di più memoria, la allocerà lentamente alla memoria massima. Se si esegue con -Xms1024m -Xmx1024m , il valore ottenuto da totalMemory() e maxMemory() sarà uguale.

Inoltre, se si desidera calcolare con precisione la quantità di memoria utilizzata , lo si fa con il seguente calcolo:

 final long usedMem = totalMemory() - freeMemory(); 

I nomi e i valori sono confusi. Se stai cercando la memoria libera totale dovrai calcolare questo valore da te. Non è quello che ottieni da freeMemory(); .

Vedi la seguente guida:

Memoria designata totale , questo sarà uguale al valore -Xmx configurato:

Runtime.getRuntime () maxMemory ().;

La memoria libera allocata corrente è lo spazio allocato attualmente pronto per i nuovi oggetti. Attenzione, questa non è la memoria disponibile totale:

Runtime.getRuntime () freeMemory ().;

Memoria allocata totale , è lo spazio allocato totale riservato per il processo java:

Runtime.getRuntime () totalMemory ().;

La memoria usata , deve essere calcasting:

usedMemory = Runtime.getRuntime (). totalMemory () – Runtime.getRuntime (). freeMemory ();

La memoria libera totale deve essere calcasting:

freeMemory = Runtime.getRuntime (). maxMemory () – usedMemory;

Un’immagine può aiutare a chiarire:

memoria di runtime java

Per capirlo meglio, esegui questo programma seguente (in jdk1.7.x):

 $ java -Xms1025k -Xmx1025k -XshowSettings:vm MemoryTest 

Questo stamperà le opzioni jvm e la memoria utilizzata , libera , totale e massima disponibile in jvm.

 public class MemoryTest { public static void main(String args[]) { System.out.println("Used Memory : " + (Runtime.getRuntime().totalMemory() - Runtime.getRuntime().freeMemory()) + " bytes"); System.out.println("Free Memory : " + Runtime.getRuntime().freeMemory() + " bytes"); System.out.println("Total Memory : " + Runtime.getRuntime().totalMemory() + " bytes"); System.out.println("Max Memory : " + Runtime.getRuntime().maxMemory() + " bytes"); } } 

Runtime # totalMemory – la memoria che la JVM ha assegnato finora. Questo non è necessariamente ciò che è in uso o il massimo.

Runtime # maxMemory – la quantità massima di memoria che la JVM è stata configurata per utilizzare. Una volta che il tuo processo raggiunge questo importo, la JVM non assegnerà più e invece GC molto più frequentemente.

Runtime # freeMemory – Non sono sicuro se questo viene misurato dal massimo o dalla porzione del totale che non è utilizzato. Sto indovinando che è una misura della parte di totale che è inutilizzata.

Le dimensioni dell’heap JVM possono essere crescibili e restringibili grazie al meccanismo Garbage-Collection. Ma non può allocare oltre la dimensione massima della memoria: Runtime.maxMemory. Questo è il significato della memoria massima. La memoria totale indica la dimensione dell’heap allocata. E la memoria libera indica la dimensione disponibile nella memoria totale.

esempio) java -Xms20M -Xmn10M -Xmx50M ~~~. Ciò significa che jvm dovrebbe allocare heap 20M all’avvio (ms). In questo caso, la memoria totale è 20M. la memoria libera è la dimensione usata da 20M. Se è necessario più heap, JVM ne alloca di più ma non può superare i 50M (mx). Nel caso del massimo, la memoria totale è 50M e la dimensione libera è di 50M. Per quanto riguarda la dimensione minima (mn), se l’heap non viene utilizzato molto, jvm può ridurre la dimensione dell’heap a 10M.

Questo meccanismo è per l’efficienza della memoria. Se un piccolo programma java viene eseguito su un’enorme memoria di heap di dimensioni fisse, una quantità di memoria insufficiente.

Versione codificata di tutte le altre risposte (al momento della scrittura):

 import java.io.*; /** * This class is based on cheneym's * awesome interpretation * of the Java {@link Runtime}'s memory query methods, which reflects intuitive thinking. * Also includes comments and observations from others on the same question, and my own experience. * 

* Runtime's memory interpretation *

* JVM memory management crash course: * Java virtual machine process' heap size is bounded by the maximum memory allowed. * The startup and maximum size can be configured by JVM arguments. * JVMs don't allocate the maximum memory on startup as the program running may never require that. * This is to be a good player and not waste system resources unnecessarily. * Instead they allocate some memory and then grow when new allocations require it. * The garbage collector will be run at times to clean up unused objects to prevent this growing. * Many parameters of this management such as when to grow/shrink or which GC to use * can be tuned via advanced configuration parameters on JVM startup. * * @see * What are Runtime.getRuntime().totalMemory() and freeMemory()? * @see * Memory Management in the Sun Java HotSpot™ Virtual Machine * @see * Full VM options reference for Windows * @see * Full VM options reference for Linux, Mac OS X and Solaris * @see * Java HotSpot VM Options quick reference */ public class SystemMemory { // can be white-box mocked for testing private final Runtime runtime = Runtime.getRuntime(); /** * Total allocated memory: space currently reserved for the JVM heap within the process. *

* Caution: this is not the total memory, the JVM may grow the heap for new allocations. */ public long getAllocatedTotal() { return runtime.totalMemory(); } /** * Current allocated free memory: space immediately ready for new objects. *

* Caution: this is not the total free available memory, * the JVM may grow the heap for new allocations. */ public long getAllocatedFree() { return runtime.freeMemory(); } /** * Used memory: * Java heap currently used by instantiated objects. *

* Caution: May include no longer referenced objects, soft references, etc. * that will be swept away by the next garbage collection. */ public long getUsed() { return getAllocatedTotal() - getAllocatedFree(); } /** * Maximum allocation: the process' allocated memory will not grow any further. *

* Caution: This may change over time, do not cache it! * There are some JVMs / garbage collectors that can shrink the allocated process memory. *

* Caution: If this is true, the JVM will likely run GC more often. */ public boolean isAtMaximumAllocation() { return getAllocatedTotal() == getTotal(); // = return getUnallocated() == 0; } /** * Unallocated memory: amount of space the process' heap can grow. */ public long getUnallocated() { return getTotal() - getAllocatedTotal(); } /** * Total designated memory: this will equal the configured {@code -Xmx} value. *

* Caution: You can never allocate more memory than this, unless you use native code. */ public long getTotal() { return runtime.maxMemory(); } /** * Total free memory: memory available for new Objects, * even at the cost of growing the allocated memory of the process. */ public long getFree() { return getTotal() - getUsed(); // = return getAllocatedFree() + getUnallocated(); } /** * Unbounded memory: there is no inherent limit on free memory. */ public boolean isBounded() { return getTotal() != Long.MAX_VALUE; } /** * Dump of the current state for debugging or understanding the memory divisions. *

* Caution: Numbers may not match up exactly as state may change during the call. */ public String getCurrentStats() { StringWriter backing = new StringWriter(); PrintWriter out = new PrintWriter(backing, false); out.printf("Total: allocated %,d (%.1f%%) out of possible %,d; %s, %s %,d%n", getAllocatedTotal(), (float)getAllocatedTotal() / (float)getTotal() * 100, getTotal(), isBounded()? "bounded" : "unbounded", isAtMaximumAllocation()? "maxed out" : "can grow", getUnallocated() ); out.printf("Used: %,d; %.1f%% of total (%,d); %.1f%% of allocated (%,d)%n", getUsed(), (float)getUsed() / (float)getTotal() * 100, getTotal(), (float)getUsed() / (float)getAllocatedTotal() * 100, getAllocatedTotal() ); out.printf("Free: %,d (%.1f%%) out of %,d total; %,d (%.1f%%) out of %,d allocated%n", getFree(), (float)getFree() / (float)getTotal() * 100, getTotal(), getAllocatedFree(), (float)getAllocatedFree() / (float)getAllocatedTotal() * 100, getAllocatedTotal() ); out.flush(); return backing.toString(); } public static void main(String... args) { SystemMemory memory = new SystemMemory(); System.out.println(memory.getCurrentStats()); } }