C# 更高效的LINQ查询

C# 更高效的LINQ查询,c#,sql,linq,C#,Sql,Linq,有人能帮我把这个查询循环变成一个高效的Linq查询吗?我正在加载到一个树状视图,所以每个项目必须附加。包括也非常低效。懒散地加载这些项也不会起作用。实际上,这个查询对数据库的访问次数比它应该访问的次数多得多 public IQueryable<Client> GetTopLevelData(Guid agentGuid, int year) { var clients = from client in ObjectContext.Clients

有人能帮我把这个查询循环变成一个高效的Linq查询吗?我正在加载到一个树状视图,所以每个项目必须附加。包括也非常低效。懒散地加载这些项也不会起作用。实际上,这个查询对数据库的访问次数比它应该访问的次数多得多

    public IQueryable<Client> GetTopLevelData(Guid agentGuid, int year)
    {
        var clients = from client in ObjectContext.Clients
                      join cbc in ObjectContext.Client_Bucket_Client on client.Client_GUID equals cbc.Client_GUID
                      join acb in ObjectContext.Agent_Client_Bucket on cbc.Client_Bucket_GUID equals acb.Client_Bucket_GUID
                      where acb.Agent_GUID == agentGuid
                      select client;

        foreach (Client c in clients)
        {
            var transactions = ObjectContext.Transactions.Where(t => t.Client_GUID == c.Client_GUID && t.Year == year);
            foreach (Transaction t in transactions)
            {
                t.Forms.Attach(ObjectContext.Forms.Where(f => f.Transaction_GUID == t.Transaction_GUID && f.Year == year)); //.OrderByDescending(fo => fo.Create_Date));
            }
            c.Transactions.Attach(transactions);
        }

        return clients;
    }
public IQueryable GetTopLevelData(Guid-agentGuid,int-year)
{
var clients=来自ObjectContext.clients中的客户端
在客户端上的ObjectContext.Client\u Bucket\u客户端中加入cbc。客户端\u GUID等于cbc.Client\u GUID
在cbc上的ObjectContext.Agent_Client_Bucket中加入acb。Client_Bucket_GUID等于acb.Client_Bucket_GUID
其中acb.Agent_GUID==agentGuid
选择客户;
foreach(客户端中的客户端c)
{
var transactions=ObjectContext.transactions.Where(t=>t.Client\u GUID==c.Client\u GUID&&t.Year==Year);
foreach(事务中的事务t)
{
t、 Forms.Attach(ObjectContext.Forms.Where(f=>f.Transaction_GUID==t.Transaction_GUID&&f.Year==Year));/.OrderByDescending(fo=>fo.Create_Date));
}
c、 交易。附上(交易);
}
返回客户;
}
公共IQueryable GetToLevel数据(Guid代理Guid,整数年)
{
var客户端=
从ObjectContext.Clients中的客户端
在客户端上的ObjectContext.Client\u Bucket\u客户端中加入cbc。客户端\u GUID等于cbc.Client\u GUID
在cbc上的ObjectContext.Agent_Client_Bucket中加入acb。Client_Bucket_GUID等于acb.Client_Bucket_GUID
其中acb.Agent_GUID==agentGuid
选择客户;
var clientinfo=
从c到客户端
选择新的
{
客户=c,
TransactionFos=ObjectContext.Transactions
其中(t=>t.Client\u GUID==c.Client\u GUID&&t.Year==Year)
.选择(t=>new
{
事务=t,
ToAttach=ObjectContext.Forms.Where(f=>f.Transaction\u GUID==t.Transaction\u GUID&f.Year==Year)/.OrderByDescending(fo=>fo.Create\u Date)
})
};
//在该查询上循环将命中数据库*一次*
foreach(ClientInfo中的var信息)
{
foreach(信息TransactionFos中的var transactionInfo)
transactionInfo.Transaction.Forms.Attach(transactionInfo.ToAttach);
info.Client.Transactions.Attach(info.transactionfos.Select(t=>t.Transaction));
}
//返回一个可查询的对象;从该对象构造新查询将再次命中数据库
返回客户;
}

对于那些关心的人来说,这是最后一个有效的代码

 var clients =
    from client in ObjectContext.Clients
    join cbc in ObjectContext.Client_Bucket_Client on client.Client_GUID equals cbc.Client_GUID
    join acb in ObjectContext.Agent_Client_Bucket on cbc.Client_Bucket_GUID equals acb.Client_Bucket_GUID
    where acb.Agent_GUID == agentGuid
    select client;

        var clientInfos =
            from c in clients
            select new
            {
                Client = c,
                TransactionInfos = ObjectContext.Transactions
                    .Where(t => t.Client_GUID == c.Client_GUID && t.Year == year)
                    .Select(t => new
                    {
                        Transaction = t,
                        ToAttach = ObjectContext.Forms.Where(f => f.Transaction_GUID == t.Transaction_GUID && f.Year == year) //.OrderByDescending(fo => fo.Create_Date);
                    })
            };

        // Looping over this query will hit the database *once*
        foreach (var info in clientInfos)
        {
            foreach (var transactionInfo in info.TransactionInfos)
            {
                transactionInfo.Transaction.Forms.Attach(transactionInfo.ToAttach);
            }

            var tt = info.TransactionInfos.ToList(); //.Select(t => t.Transaction);

            var trans = tt.Select(t => t.Transaction);

            info.Client.Transactions.Attach(trans);
        }

        // Return a queryable object; constructing a new query from this will hit the database one more time
        return clients;

我必须枚举底部的列表,才能让Linq编译器获取表单。

Linq到SQL或Linq到实体?为了使其编译,我必须稍微修改语法。不太可能,但我遇到了以下错误:查询“GetToLevel Data”的加载操作失败。具体化查询结果不支持此方法。@Inturbidus:您一定在编写的其他代码中收到了此错误,而不是在我编写的此方法中。实际上,我只更改了两个语法问题。在说Client=c的行中有一个错误,所以我将上一行改为clients中的from c,而不是clients中的from Client。我还删除了一个额外的);在ToAttach语句旁边。该错误是由foreach语句引起的。我确信代码可以正常工作,但似乎存在某种错误。这是导致错误的特定行:info.Client.Transactions.Attach(info.transactionfos.Select(t=>t.Transaction))@Inturbidus:好的,我已经修复了语法错误,但恐怕我对错误消息感到困惑,对不起。
 var clients =
    from client in ObjectContext.Clients
    join cbc in ObjectContext.Client_Bucket_Client on client.Client_GUID equals cbc.Client_GUID
    join acb in ObjectContext.Agent_Client_Bucket on cbc.Client_Bucket_GUID equals acb.Client_Bucket_GUID
    where acb.Agent_GUID == agentGuid
    select client;

        var clientInfos =
            from c in clients
            select new
            {
                Client = c,
                TransactionInfos = ObjectContext.Transactions
                    .Where(t => t.Client_GUID == c.Client_GUID && t.Year == year)
                    .Select(t => new
                    {
                        Transaction = t,
                        ToAttach = ObjectContext.Forms.Where(f => f.Transaction_GUID == t.Transaction_GUID && f.Year == year) //.OrderByDescending(fo => fo.Create_Date);
                    })
            };

        // Looping over this query will hit the database *once*
        foreach (var info in clientInfos)
        {
            foreach (var transactionInfo in info.TransactionInfos)
            {
                transactionInfo.Transaction.Forms.Attach(transactionInfo.ToAttach);
            }

            var tt = info.TransactionInfos.ToList(); //.Select(t => t.Transaction);

            var trans = tt.Select(t => t.Transaction);

            info.Client.Transactions.Attach(trans);
        }

        // Return a queryable object; constructing a new query from this will hit the database one more time
        return clients;