Groovy Documentation

groovy.lang
[Java] Annotation Type Lazy

java.lang.Object
  groovy.lang.Lazy

@Retention(RetentionPolicy.SOURCE)
@Target({ElementType.FIELD})
@GroovyASTTransformationClass("org.codehaus.groovy.transform.LazyASTTransformation")
public @interface Lazy

Field annotation to simplify lazy initialization.

Example usage without any special modifiers just defers initialization until the first call but is not thread-safe:

 @Lazy T x
 
becomes
 private T $x

 T getX() {
    if ($x != null)
       return $x
    else {
       $x = new T()
       return $x
    }
 }
 
If the field is declared volatile then initialization will be synchronized using the double-checked locking pattern as shown here:
 @Lazy volatile T x
 
becomes
 private volatile T $x

 T getX() {
    T $x_local = $x
    if ($x_local != null)
       return $x_local
    else {
       synchronized(this) {
          if ($x == null) {
             $x = new T()
          }
          return $x
       }
    }
 }
 
By default a field will be initialized by calling its default constructor. If the field has an initial value expression then this expression will be used instead of calling the default constructor. In particular, it is possible to use closure { ... } () syntax as follows:
 @Lazy T x = { [1, 2, 3] } ()
 
becomes
 private T $x

 T getX() {
    T $x_local = $x
    if ($x_local != null)
       return $x_local
    else {
       synchronized(this) {
          if ($x == null) {
             $x = { [1, 2, 3] } ()
          }
          return $x
       }
    }
 }
 

@Lazy(soft=true) will use a soft reference instead of the field and use the above rules each time re-initialization is required.

If the soft flag for the annotation is not set but the field is static, then the initialization on demand holder idiom is used as follows:

 @Lazy static FieldType field
 @Lazy static Date date1
 @Lazy static Date date2 = { new Date().updated(year: 2000) }()
 @Lazy static Date date3 = new GregorianCalendar(2009, Calendar.JANUARY, 1).time
 
becomes these methods and inners classes within the class containing the above definitions:
 private static class FieldTypeHolder_field {
     private static final FieldType INSTANCE = new FieldType()
 }

 private static class DateHolder_date1 {
     private static final Date INSTANCE = new Date()
 }

 private static class DateHolder_date2 {
     private static final Date INSTANCE = { new Date().updated(year: 2000) }()
 }

 private static class DateHolder_date3 {
     private static final Date INSTANCE = new GregorianCalendar(2009, Calendar.JANUARY, 1).time
 }

 static FieldType getField() {
     return FieldTypeHolder_field.INSTANCE
 }

 static Date getDate1() {
     return DateHolder_date1.INSTANCE
 }

 static Date getDate2() {
     return DateHolder_date2.INSTANCE
 }

 static Date getDate3() {
     return DateHolder_date3.INSTANCE
 }
 
Authors:
Alex Tkachman
Paul King


 
Optional Element Summary
boolean soft

@default false

Returns:
if field should be soft referenced instead of hard referenced

 
Method Summary
 
Methods inherited from class java.lang.Object
java.lang.Object#wait(long), java.lang.Object#wait(long, int), java.lang.Object#wait(), java.lang.Object#equals(java.lang.Object), java.lang.Object#toString(), java.lang.Object#hashCode(), java.lang.Object#getClass(), java.lang.Object#notify(), java.lang.Object#notifyAll()
 

Element Detail

soft

public boolean soft
@default false
Returns:
if field should be soft referenced instead of hard referenced


 

Groovy Documentation