Подтвердить что ты не робот

Entity Framework Code First Lazy Загрузка

У меня есть два класса объектов

public class User
{
    public Guid Id { get; set; }
    public string Name { get; set; }

    // Navigation
    public ICollection<Product> Products { get; set; }
}

public class Product
{
    public Guid Id { get; set; }

    // Navigation
    public User User { get; set; }
    public Guid User_Id { get; set; }

    public string Name { get; set; }
}

Когда я загружаю пользователя, использующего dataContext, я получаю список нулевых продуктов (это нормально).

Если я добавлю "виртуальное" ключевое слово в список продуктов,

public virtual ICollection<Product> Products { get; set; }

когда я загружаю пользователя, я также получаю список продуктов.

Почему это происходит? Я думал, что ключевое слово "virtual" используется для того, чтобы не загружать объекты, если вы не указали это (используя инструкцию "Include" )

Я думаю, что все неправильно.

4b9b3361

Ответ 1

Это неверно

"виртуальное" ключевое слово используется для того, чтобы не загружать объекты, если вы не явно это (используя инструкцию "Включить" )

Lazy Loading означает, что объекты будут автоматически загружены при первом доступе к свойству коллекции или навигации, и это произойдет прозрачно, как если бы они всегда были загружены родительским объектом.

Использование "include" - загрузка по требованию при указании свойств, которые вы хотите запросить.

Существование ключевого слова virtual связано только с ленивой загрузкой. virtual ключевое слово позволяет среде фреймворка сущности создавать динамические прокси-серверы для ваших классов сущностей и их свойств и тем самым поддерживать ленивую загрузку. Без виртуальной, ленивой загрузки не будет поддерживаться, и вы получите null на свойства коллекции.

Факт в том, что вы можете использовать "включить" в любом случае, но без ленивой загрузки это единственный способ доступа к свойствам коллекции и навигации.

Ответ 2

Я предполагаю, что вы запрашиваете свойство, которое является предметом ленивой загрузки, находясь в контексте ef:

using (var db = new Context())
{
    var user = db.Users.Where(...);

    var products = user.Products; // being loaded right away
}

Попробуйте оставить его:

User user;
using (var db = new Context())
{
    user = db.Users.Where(...);

    // I guess you will need here:
    // .Include(u => u.Products)
}
var products = user.Products; // what error will you get here?