Question

I want to use the behavior of Lazy<T> in my class to make sure that a certain operation happens once and only once. I have done this before by having a Lazy that essentially calls a Func that does something and then returns a null value. I don't care about the return value, I just want to make sure the thing only happens once.

I'm thinking it could be called Once. I'll build it myself and use a Lazy internally if it doesn't already exist, but I thought ask before doing that. Thanks!

Was it helpful?

Solution

It does not exist yet. Use a Lazy<object> and return null from the factory.

You can encapsulate that into a Once class like you said but don't inherit from Lazy<object> because that would be a misuse of inheritance. Use proper encapsulation.

You can also use the LazyInitializer class which is a matter of taste.

OTHER TIPS

If you don't need absolute control over when the initialization occurs, you could use a static constructor of one of your classes. Otherwise you could use the following:

You can either use Lazy<T> or LazyInitializer. Here is an example of the latter.

private object _initializationObject;

// this is used to ensure the initialization function only runs once, even in
// multi-threaded scenarios
private bool _initialized;
private readonly object _initializationLock = new object();

private void Initialize()
{
  // run the initialization once
  LazyInitializer.EnsureInitialized(
    ref _initializationObject, ref _initialized,
    _initializationLock, InitializeImpl);
}

private object InitializeImpl()
{
  // initialization code...

  return null;
}

As mentioned, are great ideas to achieve what you want

1) Use Lazy<object> returns null..
2) Use LazyInitializer.EnsureInitialized<T> returns null too..
3) Use a Singleton Pattern or something like it...

But I recommend another approach

Use Task initialization, you can check more details here: http://blog.stephencleary.com/2013/01/async-oop-2-constructors.html

The basics ideia is to create a task, you do not necessary need perform asynchronous, you only need to wait for its completed, and if it is completed, the method proceeds directly.

All ways are very similar, feel free to choose the one which fits in your solution.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top