简体   繁体   English

与实体框架的可选连接

[英]Optional join with Entity Framework

I have a situation when I have to load data from several table into a single object, ie I have separate tables for BasicProperties and several kinds of "advanced" properties` (I'm not allowed to refactor either the database or the object model). 当我不得不将数据从多个表加载到单个对象中时,我遇到了一种情况,即我为BasicProperties和几种“高级”属性有单独的表(不允许重构数据库或对象模型) 。

However, since loading the advanced properties is expensive, and unnecessary in most cases, I want to omit it, unless explicitly specified. 但是,由于加载高级属性非常昂贵,并且在大多数情况下是不必要的,因此除非明确指定,否则我想忽略它。

What I currently have is something like: 我目前所拥有的是:

  from basics in ctx.Basics
    join numerics in ctx.Numerics on basics.ID equals numerics.ItemID
    join alphas in ctx.Alphas on basics.ID equals alphas.Itemid
    join cplx in ctx.Complex on basics.ID equals cplx.Itemid into complex
  select new HodgePodge
             {
               Basics = basics,
               Numerics = numerics,
               Alphas = alpha,
               Complex = complex
             };

so I need some (easy) way to include / exclude the loading of the Numerics , Alphas and Complex database tables. 因此,我需要一些(简便)方法来包含/排除对NumericsAlphasComplex数据库表的加载。

Basically, I'm a "guest" on this project trying to optimize the loading code, so I'm not allowed to change the code too much, and the worst-case performance must stay at least the same. 基本上,我是这个项目上的“客人”,试图优化加载代码,因此不允许过多更改代码,并且最坏情况下的性能至少必须保持不变。

You can move your join logic into the select statement, and based on your relationship type ( 1:1, 1:* ) you use FirstOrDefault or Where 您可以将您的join逻辑到select语句,并根据您的关系类型( 1:1, 1:* )使用FirstOrDefaultWhere

bool loadNumerics = true;
bool loadAlphas  = true;
bool loadComplex = true;

var query = from basics in ctx.Basics
            select new HodgePodge
            {
               Basics = basics,
               Numerics = ctx.Numerics.FirstOrDefault(x => loadNumerics == true && basics.ID == x.ItemID),
               Alphas = ctx.Alphas.FirstOrDefault(x => loadAlphas == true && basics.ID == x.Itemid),
               Complex = ctx.Complex.Where(x => loadComplex == true && basics.ID == x.Itemid),
            };

you can try this: 您可以尝试以下方法:

IQueryable<HodgePodge> Query = ctx.Basics.Select(u => new HodgePodge(){ Basic = u }).AsQueryable();

        if(ConditionNumeric)
            Query = Query.Join(ctx.Numerics,
                q => q.Basic.ID,
                n => n.Itemid,
                (q, n) => new HodgePodge(){ Basic = q.Basic, Numeric = n })
            .AsQueryable();

        if(ConditionAlpha)
            Query = Query.Join(ctx.Alphas,
                q => q.Basic.ID,
                a => a.Itemid,
                (q, a) => new HodgePodge(){ Basic = q.Basic, Alpha = a })
            .AsQueryable();

        if(ConditionComplex)
            Query = Query.Join(ctx.Complex,
                q => q.Basic.ID,
                c => c.Itemid,
                (q, c) => new HodgePodge(){ Basic = q.Basic, Complex = c })
            .AsQueryable();

        return Query.ToList();

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM