Java Variables Initialization

Introduction

There two ways of initialize a field, eagerly and lazily. Lazy initialization is based on initializing the field when the value is needed, whereas the eager initialization is based on initializing the variable when it is declared.

Both choices are compatible with static and instance fields, however the implementations may differ when trying to achieve performance improvement.

Eager Initialization

Eager initialization is commonly used when:

private final Object eagerObject = new Object();

Lazy Initialization

Lazy initialization is recommended when:

Use Cases

As you can see it is really important to know the context of the field and how it is going to be accessed, to decide what kind of initialization is recommended. However, bear in mind that most of the time eager initialisation is recommended.

When lazy initialization and static fields are combined, the lazy initialization holder class idiom is recommended.

private static class OjbectHolder {

    static final Object object = new Object();
}

private static Object getField() { return OjbectHolder.object; }

By doing this, the static object is initialized only the first time getField() is called. In addition, the getField() method is not synchronized and it is only a field access, therefore there is no cost of access.

In case you want to use lazy initialization for an instance field use the Double Check Locking Pattern.

private volatile Object lazyIntanceObject;

private Object getLazyIntanceObject() {

    Object result = lazyIntanceObject;

    if (result == null) {  // 1st check

        synchronized(this) {

            if (lazyIntanceObject == null)  // 2nd check (locking thread)
                lazyIntanceObject = result = new Object();
        }
    }
    return result;
}

Conclusion

You should choose eager initialization over lazy initialization in most cases. Only use lazy initialisation when the performance is a priority or in order to break initialization circularity.