RU EN

How to perform lazy initialization in C#

Автор:
Joydip Kanjilal
Источник:
Просмотров:
2457
How to perform lazy initialization in C# favorites 0

Lazy initialization is a technique that defers the creation of an object until the first time it is needed. In other words, initialization of the object happens only on demand. Note that the terms lazy initialization and lazy instantiation mean the same thing — they can be used interchangeably. By taking advantage of lazy initialization, you can improve the application’s performance by avoiding unnecessary computation and memory consumption. In this article we’ll look at how we can perform lazy initialization in C#.

Let’s understand lazy loading with a simple example. Consider two classes, Customer and Order. The Customer class contains an Orders property that in turn references a collection of instances of the Order class. The Orders collection may contain a large amount of data and may even need a database connection to connect to the database and retrieve records. In such a case, there is no point in loading data in the Orders property until we need the data. Lazy initialization allows us to load the Orders collection only when the data is asked for.

Using the Lazy<T> class in C#

Although you can write your own custom code to implement lazy initialization, Microsoft recommends using the Lazy<T> class instead. The Lazy<T> class in the System namespace in C# was introduced as part of .Net Framework 4.0 to provide a thread-safe way to implement lazy initialization. You can take advantage of this class to defer the initialization of resource-intensive objects in your application.

When you use the Lazy<T> class, you need to specify the type of object you intend to create lazily in the type argument. Note that lazy initialization occurs when you access the Lazy<T>.Value property. Here is an example of how the Lazy<T> class can be used:

Lazy<IEnumerable<Order>> orders = new Lazy<IEnumerable<Order>>();
IEnumerable<Order> result = lazyOrders.Value;

Now, consider two classes, Author and Blog. An author can write many blog posts, so you have a one-to-many relationship between the Author and Blog classes as shown in the code snippet below.

public class Author
{
    public int Id { get; set; }
    public string FirstName { get; set; }
    public string LastName { get; set; }
    public string Address { get; set; }
    public List<Blog> Blogs { get; set; }
}

public class Blog
{
    public int Id { get; set; }
    public string Title { get; set; }
    public DateTime PublicationDate { get; set; }
}

Note that the one-to-many relationship between the Author and Blog classes has been represented using a List property (of type Blog) in the Author class. Using this property, the Author class can hold a collection of one or more instances of the Blog class.

Now suppose we need to display only the details of an author (first name, last name, and address) in the user interface. There is no point in loading the blog details for the author in this case; we want to load the blog details lazily. Here is the updated Author class that addresses this need. Note the usage of the Lazy<T> class.

public class Author
{
    public int Id { get; set; }
    public string FirstName { get; set; }
    public string LastName { get; set; }
    public string Address { get; set; }
    public Lazy<IList<Blog>> Blogs => new Lazy<IList<Blog>>(() => GetBlogDetailsForAuthor(this.Id));

    private IList<Blog> GetBlogDetailsForAuthor(int Id)
    {
        // Write code here to retrieve all blog details for an author.
    }
}

Using the generic Lazy class in C#

Let’s now look at how we can take advantage of a generic Lazy class to implement the Singleton design pattern. The following version of the StateManager class is thread-safe. At the same time, it demonstrates lazy initialization. Note that the explicit static constructor has been used to ensure that the C# compiler doesn’t mark the type as beforefieldinit.

public sealed class StateManager
{
    private StateManager()
    {
    }

    public static StateManager Instance
    {
        get
        {
            return Nested.obj;
        }
    }

    private class Nested
    {
        static Nested()
        {
        }
        internal static readonly StateManager obj = new StateManager();
    }
}

Here is a lazy implementation of the StateManager class that leverages the Lazy<T> class. You can see how the Lazy<T> class makes it really simple to implement laziness.

public class StateManager
{
    private static readonly Lazy<StateManager> obj = new Lazy<StateManager>(() => new StateManager());
    private StateManager() { }
    public static StateManager Instance
    {
        get
        {
            return obj.Value;
        }
    }
}

Take a look at the Instance property in the StateManager class above. Note that the Value property you see in the above code example is read-only. For that reason there is no set accessor.

Lazy initialization is an excellent performance optimization technique, allowing you to defer the initialization of objects that consume significant CPU and memory resources until you absolutely need them. Take advantage of lazy initialization to improve the performance of your apps.

Похожее
Jul 7, 2021
Author: Changhui Xu
C# has a feature, String Interpolation, to format strings in a flexible and readable way. The following example demonstrates the way how we usually output a string when we have data beforehand then pass data to the template string. var...
Apr 16, 2022
Author: Matthew MacDonald
Sometimes it’s the little things that count. When .NET 6 dropped this November, a few top-line items grabbed all the attention. I’m talking about C# 10, hot reload, Blazor’s AOT compilation, and some serious inner loop performance improvements. All of...
Sep 6, 2023
Author: Kenji Elzerman
To write files with C#, you have to know how to do it. The basics aren’t rocket science. There are a few lines of code you need to know. But writing and reading files with C# is something every beginning...
Jun 29, 2023
Author: Megha Prasad
Attributes and decorators, which allow you to attach metadata to classes, properties, and methods. Attributes Attributes in C# allow you to attach metadata to your classes, methods, and other code elements. This metadata can then be used at runtime to...
Написать сообщение
Тип
Почта
Имя
*Сообщение
RSS
Если вам понравился этот сайт и вы хотите меня поддержать, вы можете
Soft skills: 18 самых важных навыков, которыми должен владеть каждый работник
Как мы столкнулись с версионированием и осознали, что вариант «просто проставить цифры» не работает
30 вопросов на собеседовании фронтенд разработчика
Компиляция и запуск C# и Blazor внутри браузера
Как айтишнику найти работу в США и ЕС: 9 лучших ресурсов
Разработка игр на Unity: с нуля до профессионала
Using a сustom PagedList class for Generic Pagination in .NET Core
Зарплата по результатам собеседования — лучший способ сократить отклики на вакансию, а тестовые задания — избыточны
Первый рабочий день: инструкция по выживанию — 4 совета, как с комфортом выйти на новую работу
Психология удалёнки: как не слететь с катушек
Boosty
Donate to support the project
GitHub account
GitHub profile