【问题标题】:LINQ to Entities custom methodLINQ to Entity 自定义方法
【发布时间】:2016-12-28 11:04:37
【问题描述】:

在我的代码中:

context.TableA
            .Where(x =>
                x.Created >= startDate
                && context.TableB.RecordExists(x.Id, 1));

RecordExists 的定义如下:

public static bool RecordExists(this IQueryable<TableB> entity, int entityId, int entityTypeId)
{
    return entity.Any(x => x.EntityId == entityId && x.EntityTypeId == entityTypeId);
}

上面的调用失败了

NotSupportedException:LINQ to Entities 无法识别该方法 '布尔记录存在(System.Linq.IQueryable`1[TableB],Int32,Int32)' 方法,并且该方法不能翻译成商店表达式。

但如果我将查询更改为:

 context.TableA
            .Where(x =>
                x.Created >= startDate
                && context.TableB.Any(p => p.EntityId == x.Id && p.EntityTypeId == 1));

效果很好,有没有办法在查询中使用这个方法?

【问题讨论】:

  • 很遗憾,在 Linq to Entities 中无法使用 Extension 方法,因为 EF 不支持此功能。
  • 我认为您可以改用bool RecordExists&lt;T&gt;(this IEnumerable&lt;T&gt; entity, ... ;)。
  • @shA.t 为什么会这样?
  • 我不是说它会起作用!!,我说你完全可以使用通用形式;)。

标签: c# .net entity-framework linq


【解决方案1】:

尝试使用表达式

表达式定义

public Expression<Func<TableA, bool>> RecordExists(IEnumerable<TableB> entities, int entityTypeId)
{
    return a => entities.Any(b => b.Id == a.EntityId && b.EntityTypeId == entityTypeId);
}

示例

return context.TableA
    .Where(x => x.Created >= startDate)
    .Where(RecordExists(context.TableB, 1));

Entity Framework Filter

【讨论】:

    【解决方案2】:

    Linq to SQL 使用“表达式树”将 lambda 表达式转换为 sql 表达式。所以你不能使用方法,只能使用内联表达式。但是您可以使用 Linq 中的方法来收集。如果您首先在TableA 上调用.ToList() 函数,那么您可以调用方法。但是.ToList() 函数将首先检索内存中的所有内容,然后对其进行过滤。所以强烈不推荐。

    【讨论】:

    • 这不是一个选项,我宁愿选择解决方案 2
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多