Friday, February 7, 2014

All about Lazy

Software Engineers are lazy. It’s a fact.  And it is a good thing.

Lazy engineer would not copy same code over and over, she’ll extract it as a method. Lazy engineer will use a standard .NET feature (tested!) instead of rolling out his own.
Of cause we talk about good engineers. Not so good and lazy engineer will copy code around, causing support nightmare.

BTW, Visual Studio allows you to find this type of code clones: just right-click on the code block and select “Find Matching Clones in Solution”.

Later on, TFS, SVN or GIT will help you to identify those who code like that.

But enough about lazy engineers, today we are going to focus on lazy property initializes.

Let’s take a look at the typical object, that exposes a public property of collection type initialized on-demand:
SomeStrings property would be initialized when it gets accessed for the first time. So far so good.

But imagine you have 5 or 10 properties like that on a class. It is a lot of typing… (remember – lazy!)
There is a way to slightly minimize typing by using ?? operator

The ?? operator is called the null-coalescing operator. It returns the left-hand operand if operand is not null; otherwise it returns the right hand operand. So our property code can be changed like that:


But what if we have to make this property accessor thread safe?

At this point, we have a choice:  we can try to implement thread-safe property initialization yourself, like in this HorrobleObject.
I’m pretty sure I've done it right this time,  but I wouldn't bet on it.

It is possible that I missed some subtle nuance and it is going to bite me later.

So please, don’t use this code.

Fortunately for us, lazy but smart engineers, .NET framework offers the solution:

public class System.Lazy<T>

Using this class we can rewrite our code like this:

Lazy object is ideal for a singleton pattern, if you really have to have one.

It allows you to focus on business logic of you class, and not to be sidetracked by low-level details of thread-safe initializers.

Stricktly speaking, Lazy can be used not only in thread-safe scenarious, but in a regular code as well. You can indicate None, as threading mode and in this case Lazy will run without multy-threading overhead.

So, if you need to implement on–demand property initialization in your class, especially in thread-safe fashion, I strongly suggest you to use Lazy<T>!

And if you want to know, what it does under cover, you can take a look at its ~400 lines of code implementation here: http://bit.ly/1gaWjOm