Heap and memory optimization
today, a project data automatic collation function, the database tens of thousands of records and pictures to organize operations, run close to the end, broke the Java.lang.outofmemoryerror,java heap space error, Previously written programs rarely encountered this memory error, because Java has garbage collector mechanism, has not been too concerned. Today on the Internet to find some information, on this basis to do a collation.
One, heap and stack
Heap-built with new, garbage collector responsible for recycling
1. When the program starts running, the JVM gets some memory from the OS, some of it is heap memory. Heap memory is usually at the bottom of the storage address, arranged up.
2, the heap is a "run-time" data area, class instantiation object is to allocate space from the heap;
3, the allocation of space on the heap is through the "new" and other instructions established, the heap is dynamically allocated memory size, the lifetime does not have to tell the compiler beforehand;
4, unlike C + + is, Java Automatic Management heap and stack, garbage collector can automatically recycle no longer use heap memory;
5, the disadvantage is that because of the runtime to dynamically allocate memory, so memory access speed is slow.
Stacks-store basic types and reference types, fast
1, the advanced data structure, usually used to save the parameters in the method, local variables;
2, in Java, all basic types (short,int, long, byte, float, Double,boolean, char) and reference types of variables are stored in the stack;
3. The living space of the data in the stack is generally within the current scopes (by {...} an enclosed area;
4, the stack to access faster than the heap, after directly located in the CPU register;
5, the data in the stack can be shared, multiple references can point to the same address;
6, the disadvantage is that the stack data size and lifetime must be determined, lack of flexibility.
Second, memory settings
1, view the virtual machine memory situation
Long MaxControl = Runtime.getruntime (). MaxMemory ()//Get the maximum amount of memory that the virtual machine can control
long currentuse = Runtime.getruntime (). TotalMemory ()//Get the amount of memory currently used by the virtual machine
By default, the Java Virtual machine maxcontrol=66650112b=63.5625m;
Do not do anything in the situation, on my machine to measure the currentuse=5177344b=4.9375m;
2, set the memory size of the command
-xms<size> Set initial Java heap size: Sets the JVM initialization heap memory size; This value can be set to be the same as-xmx to avoid the JVM reallocating memory after each garbage collection completes.
-xmx<size> Set maximum Java heap size: Sets the maximum heap memory size for the JVM;
-xmn<size>: Set the young generation size, the entire heap size = young generation size + older generation size + persistent generation size.
-xss<size> set Java thread stack size: Sets the JVM thread stack memory size;
3, the specific operation
(1) JVM Memory settings:
Open MyEclipse (Eclipse) window-preferences-java-installed Jres-edit-default VM Arguments
Enter in VM argument:-xmx128m-xms64m-xmn32m-xss16m
(2) IDE Memory settings:
Modify the configuration under-vmargs in the Myeclipse.ini (or Eclipse.ini under the eclipse root) in the MyEclipse root directory:
(3) Tomcat memory settings
Open the Bin folder under the Tomcat root directory, edit Catalina.bat
Modified to: Set java_opts=-xms256m-xmx512m
OutOfMemoryError error Analysis in Java heap
The heap memory set by the-XMS parameter is used when the JVM is started. As the program continues to create more objects, the JVM begins to expand heap memory to accommodate more objects. The JVM also uses the garbage collector to reclaim memory. As soon as the maximum heap memory set by-XMX is reached, if no more memory can be allocated to the new object, the JVM throws the java.lang.OutOfMemoryError and the program goes down. Before throwing the OutOfMemoryError, the JVM tries to use the garbage collector to free up enough space, but when it finds that there is still not enough space, it throws the error. To solve this problem, you need to be aware of the program object's information, such as which objects you have created, what objects occupy the space, and so on. You can use the profiler or heap analyzer to handle outofmemoryerror errors. "Java.lang.OutOfMemoryError:Java heap space" means that there is not enough room for the heap to continue expanding. "Java.lang.OutOfMemoryError:PermGen space" means permanent generation is full, your program can no longer load classes or assign a string.
Iv. Heap and garbage collection
We know that objects are created in heap memory and garbage collection is a process that clears the dead objects out of heap space and returns them back to the heap. In order to use the garbage collector, the heap is mainly divided into three regions, called the new Generation,old Generation or tenured Generation, and perm space. The new generation is used to store the newly created object in space and is used when the object is new. If they are used for a long time, they will be moved by the garbage collector to the old Generation (or tenured Generation). Perm space is where the JVM holds meta data, such as classes, methods, string pools, and class-level details.
V. Summary:
1. Java heap Memory is part of the memory that the operating system allocates to the JVM.
2, when we create objects, they are stored in the Java heap memory.
3, in order to facilitate garbage collection, Java heap space into three areas, respectively called New Generation, old Generation or called tenured Generation, there are perm spaces.
4, you can adjust the size of the Java heap space by using the JVM's command-line options-XMS,-xmx,-xmn.
5. You can use Jconsole or runtime.maxmemory (), Runtime.totalmemory (), runtime.freememory () to see the size of heap memory in Java.
6, you can use the command "Jmap" to obtain heap dump, with "jhat" to analyze heap dump.
7, Java heap space is different from stack space, stack space is used to store call stacks and local variables.
8. The Java garbage collector is used to reclaim memory from dead objects (objects that are no longer used) and then to release them into the Java heap space.
9, when encountered Java.lang.outOfMemoryError, do not need to be nervous, sometimes just add heap space on it, but if often, it is necessary to see if there is memory leak in the Java program.
10. Use the profiler and heap dump analysis tools to view the Java heap space to see how much memory is allocated to each object.
Stack storage Detailed
Java stack Storage has the following features:
The data size and lifecycle in the existing stack must be determined.
such as the basic type of storage: int a = 1; This variable has a literal value, and a is a reference to the int type, pointing to the 3 literal. These literal data, due to the size of known, lifetime known (these literals are fixed in a program block, the program block exit, the literal value disappears), for the pursuit of speed reasons, exist in the stack.
Second, the existence of data can be shared in the stack.
(1), the basic type of data storage:
Such as:
The compiler first deals with int a = 3; First, it creates a reference to a variable in the stack, and then looks for an address with a literal value of 3, then opens an address that holds the face value of 3 and then points a to 3. Then deal with int b = 3, after creating the reference variable for B, the B directly points to the address of 3 because it already has 3 of the literal value on the stack. In this way, there is a case where A and B both point to 3.
Note: This literal reference differs from a reference to a class object. Assuming that references to two classes of objects also point to an object, if an object reference variable modifies the internal state of the object, then another object reference variable also instantly reflects the change. Conversely, modifying the value of a literal by reference does not result in another change in the value of the reference to that literal. As in the example above, we define the value of a and B and then make a=4; then, b is not equal to 4, or equal to 3. Inside the compiler, when A=4 is encountered, it will search the stack for a 4 literal value, and if not, reopen the address for a value of 4, and if so, point a directly to the address. Therefore the change of a value does not affect the value of B.
(2), Packaging class data storage:
Classes such as Integer, Double, String, and so on, that wrap the corresponding basic data types. All of these class data exist in the heap, and Java uses the new () statement to tell the compiler that it is dynamically created at run time, so it is more flexible, but the disadvantage is that it takes more time.
Take string, for example.
A string is a special wrapper class data. This can be created as String str = new String ("abc"), or As String str = "ABC"; The former is the process of creating a canonical class, in Java, where everything is an object, and an object is an instance of a class, all created in the form of new (). Some classes in Java, such as the DateFormat class, can return a newly created class through the getinstance () method of the class, which seems to violate this principle. Fact The class uses a singleton pattern to return an instance of a class, except that the instance is created inside the class through new (), and getinstance () hides this detail externally.
So why is it a violation of the above principles to create an instance in string str = "abc", and not through new ()? No, actually.
Internal work on string str = "abc". Inside Java, this statement is translated into the following steps:
A, first define an object reference variable named str to the String class: String str;
b, in the stack to find there is no store value of "ABC" address, if not, create an address that holds the value of "ABC", then creates an object o of the new string class, points to the address of the string value of O, and notes the object o of the reference next to this address in the stack. If you already have an address with the value "ABC", look for the object o and return the address of O.
c, point Str to the address of object o.
It is important to note that the string values are usually stored directly in the string class. But like string str = "abc"; in this case, its string value holds a reference to the data in the existing stack (that is, string str = "abc"; both stack and heap storage).
To better illustrate this issue, we can verify this by using several of the following code.
String str1 = "abc";
String str2 = "abc";
(The true value is returned only if all two references point to the same object.) Whether str1 and str2 all point to the same object
As a result, the JVM created two references str1 and str2, but only one object was created, and two references all pointed to the object.
String str1 = "abc";
String str2 = "abc";
str1 = "BCD";
System.out.println (str1 + "," + str2); BCD, ABC
System.out.println (STR1==STR2);//false
This means that the change in assignment results in a change in the reference of the class object, str1 points to another new object, and the str2 still points to the original object. In the example above, when we change the value of str1 to "BCD", the JVM discovers that there is no address in the stack that holds the value, opens up the address, and creates a new object whose string value points to the address.
In fact, the string class is designed to be an immutable (immutable) class. If you want to change its value, you can, but the JVM silently creates a new object at run time based on the new value (it cannot change its value on the original memory), and then returns the address of the object to the reference to the original class. This creation process is completely automated, but it takes up more time after all. In the environment that is sensitive to the time requirement, it will have a certain adverse effect.
String str1 = "abc";
String str2 = "abc";
str1 = "BCD";
String STR3 = str1;
System.out.println (STR3); BCD
String STR4 = "BCD";
System.out.println (str1 = = STR4); True
Str3 This object's reference directly points to the object that str1 points to (note that STR3 does not create a new object). When STR1 has finished changing its value, it creates a reference str4 for string and points to a new object created by str1 modifying the value. It can be found that this time STR4 also did not create a new object, so as to realize the stack of data sharing.
String str1 = new String ("abc");
String str2 = "abc";
System.out.println (STR1==STR2); False
Two references were created. Two objects were created. Two references point to different two objects.
String str1 = "abc";
String str2 = new String ("abc");
System.out.println (STR1==STR2); False
Two references were created. Two objects were created. Two references point to different two objects.
The above two pieces of code show that as long as the new object is created with new (), it is built in the heap and its string is stored separately, even if it is the same as the data in the stack, and is not shared with the data in the stack.
Summarize:
(1) When we use a format definition class such as String str = "ABC", We always think of course that we created the object str of the String class. Worry about the traps! The object may not have been created! The only certainty is that a reference to the string class was created. Whether or not this reference is pointing to a new object must be considered in context, unless you are creating a new object by means of the new () method. So it's more accurate to say that we created a reference variable str that points to the object of the string class, which refers to a string class with a value of "ABC". Waking up to this point is helpful in troubleshooting bugs that are hard to find in the program.
(2) The use of string str = "ABC" can improve the speed of the program to some extent, because the JVM automatically determines whether it is necessary to create a new object based on the actual situation of the data in the stack. For code with string str = new String ("abc"), the new object is created in the heap, regardless of whether its string value is equal or not, and it is necessary to create a new object, which increases the burden on the program.
(3) Because of the immutable nature of the string class (because the value of the wrapper class is not modifiable), you should consider using the StringBuffer class to improve program efficiency when the string variable needs to change its value frequently.