.NET 4.0 has a nice utility class called System.Lazy that does lazy object initialization. I would like to use this class for a 3.5 project. One time I saw an implementation somewhere in a stackoverflow answer but I can't find it anymore. Does someone have an alternative implementation of Lazy? It doesn't need all the thread safety features of the framework 4.0 version.
Updated:
Answers contain a non thread safe and a thread safe version.
The Lazy<T> object ensures that all threads use the same instance of the lazily initialized object and discards the instances that are not used.
To implement a public property by using lazy initialization, define the backing field of the property as a Lazy<T>, and return the Value property from the get accessor of the property. The Value property is read-only; therefore, the property that exposes it has no set accessor.
The type argument of the Lazy<T> object that you create specifies the type of the object that you want to initialize lazily. The constructor that you use to create the Lazy<T> object determines the characteristics of the initialization. Lazy initialization occurs the first time the Lazy<T>. Value property is accessed.
In computer programming, lazy initialization is the tactic of delaying the creation of an object, the calculation of a value, or some other expensive process until the first time it is needed. It is a kind of lazy evaluation that refers specifically to the instantiation of objects or other resources.
Here is an implementation that I use.
/// <summary> /// Provides support for lazy initialization. /// </summary> /// <typeparam name="T">Specifies the type of object that is being lazily initialized.</typeparam> public sealed class Lazy<T> { private readonly object padlock = new object(); private readonly Func<T> createValue; private bool isValueCreated; private T value; /// <summary> /// Gets the lazily initialized value of the current Lazy{T} instance. /// </summary> public T Value { get { if (!isValueCreated) { lock (padlock) { if (!isValueCreated) { value = createValue(); isValueCreated = true; } } } return value; } } /// <summary> /// Gets a value that indicates whether a value has been created for this Lazy{T} instance. /// </summary> public bool IsValueCreated { get { lock (padlock) { return isValueCreated; } } } /// <summary> /// Initializes a new instance of the Lazy{T} class. /// </summary> /// <param name="createValue">The delegate that produces the value when it is needed.</param> public Lazy(Func<T> createValue) { if (createValue == null) throw new ArgumentNullException("createValue"); this.createValue = createValue; } /// <summary> /// Creates and returns a string representation of the Lazy{T}.Value. /// </summary> /// <returns>The string representation of the Lazy{T}.Value property.</returns> public override string ToString() { return Value.ToString(); } }
If you don't need thread-safety, it's pretty easy to put one together with a factory method. I use one very similar to the following:
public class Lazy<T> { private readonly Func<T> initializer; private bool isValueCreated; private T value; public Lazy(Func<T> initializer) { if (initializer == null) throw new ArgumentNullException("initializer"); this.initializer = initializer; } public bool IsValueCreated { get { return isValueCreated; } } public T Value { get { if (!isValueCreated) { value = initializer(); isValueCreated = true; } return value; } } }
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With