Since the work, the more written code, the program is increasingly bloated, less efficient, for me such a pursuit of the perfect programmer, this is absolutely not allowed, so in addition to constantly optimize the program structure, memory optimization and performance tuning has become my usual "trick."
To perform memory optimization and performance tuning on Java programs, do not understand the internal principle of the virtual machine (or the specification is more rigorous point) is certainly not, here recommend a good book "Deep Java Virtual Machine (second edition)" (Bill Venners, Cao Xiaogang Shang translation, actually this article is the author after reading this book , an elaboration of the personal understanding of Java virtual machines). Of course, understanding the benefits of Java virtual machines is not limited to these two benefits. From a deeper technical level, understanding the specification and implementation of Java virtual machines will help us write efficient, stable Java code. For example, if you understand the memory model of a Java virtual machine, understanding the memory recovery mechanism of a virtual machine, we don't rely too much on it, but explicitly "free up memory" when needed (Java code cannot explicitly release memory, but you can tell the garbage collector to recycle the object by releasing the object reference). To reduce unnecessary memory consumption; If we understand how the Java stack works, then we can reduce the risk of stack overflow by reducing the number of recursive layers and reducing the number of loops. It may not be possible for application developers to directly address the underlying implementation of these Java virtual machines, but the knowledge of these backgrounds, more or less, will have a subtle effect on the programs we write.
This article, will be concise description of the Java Virtual Machine architecture and memory model, such as improper use of words or interpretation of inaccuracies, please do not hesitate, deeply honored!
Java Virtual Machine Architecture
Class loading Subsystem
The Java Virtual machine has two kinds of loaders, namely, the Boot class loader and the user custom loader.
The Pass class loading subsystem loads the class into the Run-time data area through its fully qualified name (package name and class name, Network load also including URL). For each loaded type, the Java virtual machine creates an instance of the Java.lang.Class class to represent the type, which is placed in the heap area in memory, and the type information of the mount is in the method area, as is the case with all other objects.
In addition to locating and importing the corresponding binary class files, the class loader subsystem verifies the correctness of the imported classes, assigns and initializes the memory for the class variables, and parses the symbolic references into direct references, which are strictly in the following order, before loading a type:
1 Load--Find and load binary data of type;
2 connection-Perform validation, preparation, and resolution (optional)
3 Verify that the type being imported is correct
4 to allocate memory for class variables and initialize them to default values
5) parsing converts symbolic references in a type to direct application
Method area
For each type loaded by the class loader subsystem, the virtual machine saves the following data to the method area:
1. Fully qualified name of the type
2. Fully qualified name of type superclass (Java.lang.Object does not have super Class)
3. Type is a class type or an interface type
4. Type of access modifier
5. Fully qualified name ordered list of any direct Super interface
In addition to the basic type information above, the following information is also saved:
6. Type of constant pool
7. Field information (including field name, field type, field modifier)
8. Method information (including method name, return type, number and type of parameters, method modifiers, if the method is not abstract and local, also saves the method's bytecode, operand stack, and the size of the local variable area and the exception table in the method stack frame)
9. All class variables other than constants (in fact, static variables for classes, because static variables are shared by all instances and are directly related to types, so they are class-level variables that are stored in the method area as members of the class)
10. A reference to the class ClassLoader
The return is just saved by the ClassLoader reference
String.class.getClassLoader ();
A reference to class classes/
/will return the reference String.class of the class classes just saved
;
Note that the method area can also be reclaimed by the garbage collector.
Heap
All class instances or arrays that the Java program creates at run time are placed in the same heap, and each Java Virtual machine also has a heap space, and all threads share a heap (this is why a multithreaded Java program can cause object access synchronization problems).
Since each Java virtual machine has a different implementation of the virtual machine specification, we may not know how each Java Virtual machine represents an object instance in the heap, but we can take a peek at the possible implementation below:
Program counter
For running Java programs, each thread has its own PC (program counter) register, which is created at the start of the thread, a word size, to hold the position of the next line of code that needs to be executed.
Java stack
Each thread has a Java stack that holds the running state of the thread in a stack frame. The virtual machine operates on the Java stack in two ways: a stack and a stack, both of which have been framed as units. The stack frame holds data such as incoming parameters, local variables, and intermediate results, which are ejected when the method completes, and then released.
Take a look at the memory snapshots of the stack frame when two local variables are added
Local method Stack
This is where Java invokes the local library of the operating system to implement JNI (Java Native Interface,java local interface)
Execution engine
The core of the Java virtual machine, controls loading Java bytecode and parsing; for running Java programs, each thread is an instance of a stand-alone virtual machine execution engine, from the beginning of the thread lifecycle to the end, either executing the bytecode or executing the local method.
Local interface
The local method stack and the operating system library are connected.
Note: All references to "Java virtual machines" in this article refer to the Java Virtual Machine specification for both Java EE and javase platforms.
Virtual Machine Memory Optimization Practice
Now that memory is mentioned, you have to talk about memory leaks. As we all know, Java is from C + + based on the development, and the C + + program A big problem is that the memory leak is difficult to solve, although the Java JVM has its own garbage collection mechanism to reclaim memory, in many cases, Java program developers do not need to do too much heart, But there are leaks, just a little less than C + +. For example, there is a referenced but useless object in the program: The program references the object, but the subsequent no or no longer uses it, and the memory space it consumes is wasted.
Let's take a look at how the GC works: monitor the running state of each object, including the object's application, references, references, assignments, and so on, when the object is no longer referenced, releasing the object (the focus of the GC article is not overly elaborated). Many Java programmers rely too much on GC, but the problem is that regardless of how well the JVM's garbage collection is doing, memory is always a limited resource, so even if the GC completes most of the garbage collection for us, it is necessary to pay due attention to the memory optimizations in the encoding process. This can effectively reduce the number of GC, while increasing memory utilization, to maximize the efficiency of the program.
In general, memory optimization for Java virtual machines should start with two aspects: Java Virtual machines and Java applications. The former means that the virtual machine's logical memory partition size is controlled by the virtual machine parameters according to the design of the application, so that the memory of the virtual machine and the program need to complement each other; the latter refers to the optimization program algorithm, reduces the GC burden, enhances the GC recovery success rate.
Parameters to optimize virtual machine memory are as follows:
Xms
Initial Heap Size
Xmx
Java Heap max value
Xmn
Young generation's heap size
Xss
stack size for each thread
There are three more commonly used parameters, and some:
Xx:minheapfreeratio=40
Minimum percentage of heap free over GC to avoid expansion.
Xx:maxheapfreeratio=70
Maximum percentage of heap free over GC to avoid shrinking.
xx:newratio=2
Ratio of new/old generation sizes. [Sparc-client:8; x86-server:8; x86-client:12.] -client:8 (1.3.1+), X86:12]
xx:newsize=2.125m
Default size of new generation (in bytes) [5.0 and newer:64 bit VMs are scaled 30%; larger; x86:1m, x86 and 5.0 0K]
Xx:maxnewsize=
Maximum size of new generation (in bytes). Since 1.4, Maxnewsize is computed as a function of newratio.
Xx:survivorratio=25
Ratio of Eden/survivor space size [Solaris amd64:6; Sparc in 1.3.1:25; Other Solaris platforms in 5.0 and EARLIER:32]
Xx:permsize=
Initial size of permanent generation
xx:maxpermsize=64m
Size of the permanent Generation. [5.0 and newer:64 bit VMs are scaled 30% larger; 1.4 amd64:96m;]
The following is said through the optimization program algorithm to improve memory utilization, and reduce the risk of memory, is entirely a experience, for reference only, if there is no problem, please correct me, thank you!
1. Early release of references to unwanted objects (XX = null;)
Read a piece of code:
Public list<pagedata> Parse (HtmlPage page) {list<pagedata> List = null;
try {List valuelist = Page.getbyxpath (Config.getcontentxpath ());
if (ValueList = null | | valuelist.isempty ()) {return list;
/////when needed to create objects, save memory, improve efficiency list = new arraylist<pagedata> ();
Pagedata pagedata = new Pagedata ();
StringBuilder value = new StringBuilder ();
for (int i = 0; i < valuelist.size (); i++) {HtmlElement content = (htmlelement) valuelist.get (i);
Domnodelist
2. Careful use of collection data types, such as arrays, trees, graphs, lists and other data structures, these data structures for GC recovery more complex.
3. Avoid the explicit application of the array space, you have to explicitly apply, as far as possible accurately estimate its reasonable value.
4. Avoid creating and initializing a large number of objects in the default constructor of the class to prevent unnecessary waste of memory resources when invoking the constructor of its own class
5. Try to avoid forcing the system to do garbage memory recovery, growth system to do garbage collection of the final time
6. Try to do remote method call class application development using instantaneous value variables, unless the remote caller needs to get the value of the instantaneous value variable.
7. Use object pooling technology to improve system performance in the right scenario