Kotlin patterns: Decorator pattern with delegated properties, and lazy initialization.

Photo by Andy Kelly on Unsplash

Differently from my article about class delegation, this pattern is applied to properties which delegate the accessors to helper objects.

Basics

In essence what we do is telling kotlin using the keyword by that the accessors of the property will be handled by an object.

The delegated object must convey the rules of the convention for property delegates. These rules are that they must implement getValue, and in case of a mutable property also a setValue.

Internally Kotlin will create an intermediate and hidden property initialized with an instance of the delegated object, Delegate()in this case.

Now any time that you try to get myVar , the returned value will be the one that the Delegate classgetValue returns. Similar will happen if we try to set a new value, in this case the function setValue of the Delegate class will be in charge of the update.

Lazy initialization

A good example of delegated properties use in Kotlin is the lazy initialization.

The lazy initialization pattern is used when we have a resource whose initilization consumes a lot of resources and we want to postpone its initialization as much as we can, normally until it first use.

To implement this behaviour by hand we will need to do a couple of things. Let see it in an example with Employe and the list of commercial calls they made. Getting all the list of commercial calls use a lot of resources so we want to load them only in case we explicitly need them.

We will use the backing property technique where we use a backingCalls property to store the data which calls delegates on.

Although this code is simple, it has a lot of boilerplate that we will need to rewrite in every property we want to have a lazy initialization. Kotlin help us with its specific delegate: by lazy

The benefits of the kotlin aproach are:

  • Is much simpler to write and read.
  • Encapsulates the backing property.
  • Hides the logic that ensures that the value is initialized only once.
  • Is thread-safe by default

Database access with delegated properties

Just to present another example of the use of delegated properties lets think that we want to abstract the access to our database using a delegated property.

We want to read and write in our classes and that the information we access is retrieved and updated in our database.

For this we will just create a delegate that handles the database access and any time we get or set a value to our class it will be done in the database.

This is a simplification of what you can see in the JetBarins Exposed Framework. If you want to learn more I recommend you to check the repo.

Conclusion

We learnt how delegated properties work in Kotlin, and analyzed the lazy initialization. It let you reuse the logic of how values are stored, accessed and initialized simplifying your code and improving its performance.

Android-Kotlin Developer

Android-Kotlin Developer