我如何知道Entity Framework的Eager Loading工作? [英] How do I know that Entity Framework's Eager Loading is working?

查看:96
本文介绍了我如何知道Entity Framework的Eager Loading工作?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个具有三个独立的子实体的实体,所有这些实体都需要在数据库中加载一个命中(典型的加载情景,我想象)。



当我在下面进行调用时:

  public IQueryable<参与者GT; GetAllWithAllIncluded()
{
dbSet.Include(p => p.EmailNotices).Load();
dbSet.Include(p => p.EmailTemplatePlaceholders).Load();
dbSet.Include(p => p.Actions).Load();
return dbSet;
}

它在SQL配置文件中进行以下输入:

  SQL:BatchStarting SELECT ... 
SQL:BatchCompleted SELECT ...
SQL:BatchStarting SELECT ...
SQL:BatchCompleted SELECT ...
SQL:BatchStarting SELECT ...
SQL:BatchCompleted SELECT ...
RPC:已完成exec sp_executesql N'SELECT ...

这是否意味着在一些批量批处理命令中只对数据库进行了一次实际的调用/命中?或者是4个单独的命中?



当我从代码中删除 .Load()时,我得到这在SQL Profiler中:



当我进行以下调用时:

  public IQueryable< Participant> GetAllWithAllIncluded()
{
dbSet.Include(p => p.EmailNotices);
dbSet.Include(p => p.EmailTemplatePlaceholders);
dbSet.Include(p => p.Actions);
return dbSet;
}

我在SQL Profiler中得到这个:

  RPC:已完成exec sp_executesql N'SELECT ... 
RPC:已完成exec sp_executesql N'SELECT ...
RPC:已完成exec sp_executesql N'SELECT ...
RPC:已完成exec sp_executesql N'SELECT ...

更新1

只是为了澄清,方法返回之后,我会粘贴几个。()子句,然后立即.ToList()它。



更新2

按照建议,我包括的地址和列表代码:

 列表<参与者>参与者= GetFilteredParticipants(repo,model,accountID).ToList(); 

它调用的函数:

  private IQueryable< Participant> GetFilteredParticipants(ParticipantRepository repo,ParticipantRequestModel model,string accountID)
{

IQueryable< Participant>参与者= repo.GetAllWithAllIncluded();

Particip = Particip.Where(p => p.Transaction.Account.AccountID == accountID || p.Transaction.Account.ParentID == accountID);

if(model.ID!= null)
{
Particip = participant.Where(p => p.ID == model.ID);
}
如果(model.ParticipantIdentifier!= null)
{
Particip = Particip.Where(p => p.ParticipantIdentifier == model.ParticipantIdentifier);
}
if(model.TransactionID!= null)
{
Particip = participant.Where(p => p.TransactionID == model.TransactionID);
}

... more wheres

Particip.Where(p => p.EmailNotices.Any(e => e.ParticipantID == p .ID))。其中(p => p.EmailTemplatePlaceholders.Any(e => e.ParticipantID == p.ID))。其中(p => p.Actions.Any(e => ParticipantID == p.ID));

返回参与者;
}


解决方案

尝试

  dbSet.Include(p => p.EmailNotices)
.Include(p => p.EmailTemplatePlaceholders)
.include(p => p.Actions)
.Load();

这应该导致单个数据库访问,通过单个SELECT加载所有数据。


I have an entity with three separate child entities that all need to be loading in one hit to the database (typical eager loading scenario, I would imagine).

When I make the the call below:

public IQueryable<Participant> GetAllWithAllIncluded()
{
    dbSet.Include(p => p.EmailNotices).Load();
    dbSet.Include(p => p.EmailTemplatePlaceholders).Load();
    dbSet.Include(p => p.Actions).Load();
    return dbSet;
}

It makes the following entries in the SQL Profile:

SQL:BatchStarting   SELECT ...      
SQL:BatchCompleted  SELECT ...
SQL:BatchStarting   SELECT ...      
SQL:BatchCompleted  SELECT ...      
SQL:BatchStarting   SELECT ...      
SQL:BatchCompleted  SELECT ...
RPC:Completed   exec sp_executesql N'SELECT ...

Does this mean that only one actual call/hit was made to the database in some soft of batch command? Or is it making 4 separate hits?

When I remove the .Load() from the code, I get this in SQL Profiler:

When I make the the call below:

public IQueryable<Participant> GetAllWithAllIncluded()
{
    dbSet.Include(p => p.EmailNotices);
    dbSet.Include(p => p.EmailTemplatePlaceholders);
    dbSet.Include(p => p.Actions);
    return dbSet;
}

I get this in SQL Profiler:

RPC:Completed   exec sp_executesql N'SELECT ...
RPC:Completed   exec sp_executesql N'SELECT ...
RPC:Completed   exec sp_executesql N'SELECT ...
RPC:Completed   exec sp_executesql N'SELECT ...

UPDATE 1
Just to clarify, after the method returns, I tack on a few .Where() clauses and then I immediately .ToList() it.

UPDATE 2
As recommended, I'm including the where and list code:

List<Participant> participants = GetFilteredParticipants(repo, model, accountID).ToList();

And the function it calls:

private IQueryable<Participant> GetFilteredParticipants(ParticipantRepository repo, ParticipantRequestModel model, string accountID)
{

    IQueryable<Participant> participants = repo.GetAllWithAllIncluded();

    participants = participants.Where(p => p.Transaction.Account.AccountID == accountID || p.Transaction.Account.ParentID == accountID);

    if (model.ID != null)
    {
        participants = participants.Where(p => p.ID == model.ID);
    }
    if (model.ParticipantIdentifier != null)
    {
        participants = participants.Where(p => p.ParticipantIdentifier == model.ParticipantIdentifier);
    }
    if (model.TransactionID != null)
    {
        participants = participants.Where(p => p.TransactionID == model.TransactionID);
    }

    ... more wheres

    participants.Where(p => p.EmailNotices.Any(e => e.ParticipantID == p.ID)).Where(p => p.EmailTemplatePlaceholders.Any(e => e.ParticipantID == p.ID)).Where(p => p.Actions.Any(e => e.ParticipantID == p.ID));

    return participants;
}

解决方案

Try

dbSet.Include(p => p.EmailNotices)
     .Include(p => p.EmailTemplatePlaceholders)
     .Include(p => p.Actions)
     .Load();

This should result in a single database access that loads all data with a single SELECT.

这篇关于我如何知道Entity Framework的Eager Loading工作?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆