10
I've defined a generic class "Lazy<T>", for lazy evaluation and caching of the result of a delegate Func<T>.
I also define two implicit cast operators so I can create a Lazy<T> from a Func<T>s, and I can assign a Lazy<T> to a T (gets the Value of the Lazy<T>)
The idea is that you can pass around a Lazy<T> in place of an instance of T, but not do the work to calculate/retrieve the value until it is assigned to an actual instance of T.
// class Lazy<T>
// Encapsulates a value which can be retrieved when first accessed,
// and is then cached.
class Lazy<T>
{
private Func<T> _getter;
private T _cached;
private bool _isCached;
// Get/set the getter delegate
// that 'calculates' the value.
public Func<T> Getter
{
get
{
return _getter;
}
set
{
_getter = value;
_cached = default(T);
_isCached = false;
}
}
// Get/set the value.
public T Value
{
get
{
if (!_isCached)
{
_cached = Getter();
_isCached = true;
_getter = null;
}
return _cached;
}
set
{
_cached = value;
_isCached = true;
_getter = null;
}
}
// Implicit casts:
// Create a T from a Lazy<T>
public static implicit operator T(Lazy<T> lazy)
{
return lazy.Value;
}
// Create a Lazy<T> from a Func<T>
public static implicit operator Lazy<T>(Func<T> getter)
{
return new Lazy<T> {Getter = getter};
}
}
But this class doesn't work as I expected in one case, highlighted in the test app below:
class Program
{
static void Main()
{
// This works okay (1)
TestLazy(() => MakeStringList());
// This also work