...
Since JDK 1.2, the new generational garbage collector has eased out reduced memory allocation related costs to minimal levels, even lesser than C/C++. Deallocation has also become cheaper wherein the cost of garbage collection is commensurate with the number of live objects in the younger generation and not the total number of objects allocated since the last run. Note that objects in the younger generation that persist for longer duration are )tenured_ . Very few younger generation objects continue to live through to the next garbage collection cycle; the rest become ready to be collected in the impending collection cycle.
...
Code Block | ||
---|---|---|
| ||
public class MutableHolder { private Hashtable<Integer, String> value; // not final public Object getValue() { return value; } public void setValue(Hashtable<Integer, String> ht) { value = (Hashtable<Integer, String>)ht; } } |
This example also violates OBJ37-J. Defensively copy private mutable class members before returning their references.
...
This compliant solution highlights a custom container called ImmutableHolder
. To aid garbage collection, it is recommended that short-lived ImmutableHolder
objects be created by passing Hashtable
instances to the constructor. When value
is assigned in ImmutableHolder
's constructor during object creation, it is a younger member field (of type ImmutableHolder.Hashtable<Integer, String>
) that is referencing an older object (of type Hashtable<Integer, String>). This is a much better position to be in as far as the garbage collector is concerned. Note that a shallow copy is used in this case to preserve references to the older value.
...
Reference nulling to "help the garbage collector" is unnecessary. In fact, it just adds clutter to the code and may introduce sometimes introduces subtle bugs. Assigning null
to local variables is also not very useful as the Java Just-In-Time compiler (JIT) can equivalently do a liveness analysis. A related bad practice is to use a finalizer to null
out references, thereby causing . This practice can cause a huge performance hit.
Code Block | ||
---|---|---|
| ||
int[] buffer = new int[100]; doSomething(buffer); buffer = null // noNo need forto explicitly assigningassign null |
Compliant Solution
Wiki Markup |
---|
TheThis code snippet shown below improves on the discouraged practice compliant solution improves by narrowing down the scope of the variable {{buffer}} so that the garbage collector collects the object as soon as it goes out of scope. \[[Bloch 08|AA. Java References#Bloch 08]\] |
...
Array based data structures such as ArrayLists
are an exception as exceptions because the programmer has to explicitly set only a few of the array elements to null
to indicate their absence or demise.
Long-lived objects containing short-lived objects
...
The garbage collector can be explicitly invoked by calling the System.gc()
method. Even though the documentation says that it "Runs the garbage collector", there is no guarantee on when the garbage collector will actually run because the call only suggests a that it will subsequently execute. Other reasons include,
- Irresponsible use of this feature can severely degrade system performance as the garbage collector would not wait until ripe periods when it is safe to garbage collect without interrupting the program's execution significantly.
- The application does not have enough information available on when to call
System.gc()
.
...