Abstract: Garbage collection is the best example of a daemon thread because it always runs in the background.

This article is shared by Hai Yong in huawei Cloud community.

introduce

In C/C++, the programmer is responsible for object creation and destruction. Programmers often ignore the destruction of useless objects. Because of this oversight, at some point there may not be enough memory available in order to create new objects, and the entire program will terminate abnormally, resulting in OutOfMemoryErrors.

But in Java, programmers don’t need to care about all the objects they no longer use. The garbage collection mechanism destroys these objects automatically.

The garbage collection mechanism is the best example of a daemon thread because it always runs in the background.

The main goal of the garbage collection mechanism is to free up heap memory by destroying unreachable objects.

Important terms

1. Unreachable objects: An object is unreachable if it does not contain any references to it. Also note that objects belonging to the quarantine island are also inaccessible.

Integer i = new Integer(4); // The new Integer object can be accessed by reference in 'I' I = null; // The Integer object is no longer available.Copy the code

2. Eligibility for garbage collection: If an object is unreachable, it is eligible for garbage collection. In the figure above, after _i = null; Integer object 4 in the heap area is eligible for garbage collection.

Methods to make objects eligible for GC

Even though the programmer is not responsible for destroying useless objects, it is strongly recommended that the object be made inaccessible (and therefore eligible for GC) if it is no longer needed.

There are generally four different ways to make an object suitable for garbage collection.

1. Dereference variables

2. Reassign reference variables

3. Objects created inside the method

4. The isolated island

All of the above approaches with examples are discussed in a separate article: How to make an object eligible for garbage collection

How the JVM is asked to run the garbage collector

Once we make an object eligible for garbage collection, the garbage collector may not destroy it immediately. Whenever the JVM runs the garbage collector, only objects are destroyed. But when the JVM is running a Garbage Collector, we can’t predict that.

We can also request the JVM to run the garbage collector. There are two ways to do this:

1. Use the system.gc () method: The System class contains the static method _gc()_ that requests the JVM to run the garbage collector.

2. Use the Runtime.geTruntime ().gc() method: The Runtime class allows the application to interact with the JVM running the application. Therefore, by using its GC () method, we can ask the JVM to run the garbage collector.

Public class Test {public static void main(String[] args) throws InterruptedException { Test t1 = new Test(); Test t2 = new Test(); // dereference t1 = null; // Request the JVM to run the garbage collector system.gc (); // dereference t2 = null; // Request the JVM to run the garbage collector Runtime.getruntime ().gc(); } @override // Call the finalize method once on the object before garbage collection. Protected void Finalize () throws Throwable {system.out.println (" garbage collector call "); System.out.println(" Object garbage collection: "+ this); }}Copy the code

Output:

Garbage collector invokes object garbage collection: haiyong.Test@7ad74083 Garbage collector invokes object garbage collection: haiyong.Test@7410a1a9Copy the code

Notes:

  • There is no guarantee that either method will run the garbage collector.

  • Calling _system.gc ()_ is equivalent to calling runtime.getruntime ().gc()

Finalized:

  • Just before the object is destroyed, the garbage collector calls the object’s _Finalize ()_ method to perform the cleanup activity. Once the _Finalize ()_ method completes, the garbage collector destroys the object.

  • The Finalize () method exists in the Object class with the following stereotypes.

    protected void finalize() throws Throwable

Depending on our requirements, we can override the _Finalize ()_ method to perform our cleanup activities, such as closing database connections.

Notes:

1. Garbage collector not _Finalize ()_ method called by JVM. Although the garbage collector is a module of the JVM.

2. The object class Finalize () method has no implementation, so it is recommended to override the _Finalize ()_ method to handle system resources or perform other cleanup.

3. For any given object, the Finalize () method will never be called more than once.

4. If the _Finalize ()_ method throws an uncaught exception, the exception is ignored and finalization of the object is terminated.

For an example of the _Finalize ()_ method, see garbage collection in Output Set 10 of a Java program

Let’s take a real-world example where we use the concept of the garbage collector.

Let’s say you go to ByteDance for an internship, and they tell you to write a program that counts the number of employees working at the company (not including interns). To make this program, you must use the concept of garbage collector.

Here are the actual tasks you get in your company:

Q: Write a program to create a class named Employee that has the following data members. 1. An ID that stores the unique ID assigned to each employee. 2. Name of employee. 3. Age of employees.

In addition, provide the following methods –

1. Parameterized constructors for initializing names and ages. The ID should be initialized in this constructor.

2. Display ID, name, and age method show().

3. ShowNextId () displays the ID of the next employee.

A beginner who doesn’t understand garbage collection today might write code like this:

Class Employee {private int ID; private String name; private int age; private static int nextId=1; Public Employee(String name,int age) {this.name = name; // It is static because it remains common and shared by all objects. this.age = age; this.ID = nextId++; } public void show() { System.out.println ("Id="+ID+"\nName="+name+"\nAge="+age); } public void showNextId() { System.out.println ("Next employee id will be="+nextId); } } class UseEmployee { public static void main(String []args) { Employee E=new Employee("GFG1",33); Employee F=new Employee("GFG2",45); Employee G=new Employee("GFG3",25); E.show(); F.show(); G.show(); E.showNextId(); F.showNextId(); G.showNextId(); {// This is the subblock that keeps all interns. Employee X=new Employee("GFG4",23); Employee Y=new Employee("GFG5",21); X.show(); Y.show(); X.showNextId(); Y.showNextId(); } // After the braces, X and Y are removed. So it should now show nextId as 4. E.showNextId(); // The output of this line should be 4, but it will give 6 as output. }}Copy the code

Now get the correct output: Now the garbage collector (GC) will see two free objects. Now decrement nextId, gc(garbage Collector) will only call the method Finalize () when our programmer overrides it in our class. As mentioned earlier, we must request a GC (Garbagecollector), to do so, we must write the following three steps before closing the braces on the subblock.

1. Set the reference to null (i.e. X = Y = null;)

2. Call system.gc ();

3. call, system.runfinalization ();

Now the correct code to count employees (excluding interns)

Class Employee {private int ID; private String name; private int age; private static int nextId=1; Public Employee(String name,int age) {this.name = name; // It is static because it remains common and shared by all objects. this.age = age; this.ID = nextId++; } public void show() { System.out.println ("Id="+ID+"\nName="+name+"\nAge="+age); } public void showNextId() { System.out.println ("Next employee id will be="+nextId); } protected void finalize() { --nextId; // In this case, GC calls Finalize () twice for 2 objects. Public static void main(String []args) {Employee E=new Employee("GFG1",33); Employee F=new Employee("GFG2",45); Employee G=new Employee("GFG3",25); E.show(); F.show(); G.show(); E.showNextId(); F.showNextId(); G.showNextId(); {// This is the subblock that keeps all interns. Employee X=new Employee("GFG4",23); Employee Y=new Employee("GFG5",21); X.show(); Y.show(); X.showNextId(); Y.showNextId(); X = Y = null; System.gc(); System.runFinalization(); } E.showNextId(); }}Copy the code

Click to follow, the first time to learn about Huawei cloud fresh technology ~