c# - "Or"Together Expression<Func<EntityFramework Entity, bool>> in .NET 4, Silverlight RIA 域服务

标签 c# silverlight-4.0 linq-to-entities entity-framework-4 expression

我有一个小的自定义对象定义为:

public class TimeSeriesDefinition
{  
    public int classID;
    public DateTime startTime;
    public DateTime endTime;
}

我将一个 List classIDs、一个 List startTimes 和一个 List endTimes 传递到一个 RIA 域服务函数中。作为组织问题,我将这些值分组到 TimeSeriesDefinitions 列表中,然后尝试使用 foreach 循环创建一个表达式,该表达式将在类中的值之间使用 AND 运算符进行选择,在每个类之间使用 OR 运算符进行选择,或者实现一个“.Any”查询,如我在下面收到的第一个答案所建议的那样。问题是我不能在 DomainService 函数中使用 TimeSeriesDefinition 类,因为它不是原始类型或我的实体类型之一(也许我应该用这种类型创建一个实体?),所以我需要另一种方法来实现想要的查询结果。我使用表达式的最初想法是我从未有过的地方:

        Expression<Func<EventLog, bool>> bounds;
        Boolean assignedBounds = false;
        foreach (TimeSeriesDefinition ts in reporters)
        {
            if (assignedBounds.Equals(false))
            { 
                bounds = c => c.reporterID == ts.classID && c.reportDateTime >= ts.startTime && c.reportDateTime <= ts.endTime; 
                assignedBounds = true;
            }
            else
            { 
                Expression<Func<EventLog, bool>> newBounds = c => c.reporterID == ts.classID && c.reportDateTime >= ts.startTime && c.reportDateTime <= ts.endTime;
                bounds = Expression.Or(Expression.Invoke(bounds), Expression.Invoke(newBounds);
                // bounds = Expression<Func<EventLog, bool>>.Or(bounds, newBounds);
            }
        }

        return this.ObjectContext.EventLog.Where(bounds);

我的目标是让结果集在 ts.startDate 和 ts.EndDate 之间有一个 ts.classID 的所有记录。从我在网上找到的内容来看,确保正确分配参数似乎也很棘手,但现在我仍然得到一个

“无法将类型‘System.Linq.Expressions.BinaryExpression’隐式转换为‘System.Linq.Expressions.Expression>’”

行错误

 bounds = Expression.Or(Expression.Invoke(bounds), Expression.Invoke(newBounds);

谁能指出我正确的方向?我想我可能会以某种方式将整个内容构建到查询字符串中,但我不想去那里。

预先感谢您的见解!

最佳答案

如果您在客户端 Funcletize(本地化)您对 TimeSeriesDefinition 的引用,您应该能够将它们包含在您的查询中(参见此处的 Evaluator.PartialEval 方法 http://msdn.microsoft.com/en-us/library/bb546158.aspx)。您应该能够简单地在您的 Expression 对象上调用它,并将对 TimeSeriesDefinitions 的引用提升为原始常量:

Evaluator.PartialEval(lambdaExpression);

至于你的编译问题:

bounds = Expression.Or(Expression.Invoke(bounds), Expression.Invoke(newBounds);

该赋值的左侧是一个通用的 LambdaExpression。右侧是 BinaryExpression。要进行分配,您需要 Lambda the Or 并为您的 InvocationExpressions 提供一个 ParameterExpression:

var parameterExpression = Expression.Parameter(typeof(EventLog));
bounds = Expression.Lambda<Func<EventLog, bool>>(  
    Expression.Or(  
         Expression.Invoke(bounds, parameterExpression),  
         Expression.Invoke(newBounds, parameterExpression), 
    parameterExpression);

但是...您可能会遇到一个奇妙的事实,即 RIA 不支持 InvocationExpressions...(我尚未验证这一点,但我知道 EF 不支持)。您必须展开您的 InvocationExpressions 以内联它们(有点像上面提到的 Funcletlizer)。

LINQKit ( http://www.albahari.com/nutshell/linqkit.aspx ) 提供了一个开箱即用的工具。它还提供了用于组合标准的辅助方法,如您上面提到的。如果你不想完全依赖于 LINQKit,你可以在这里获取相同内容的源代码:http://www.java2s.com/Open-Source/CSharp/Content-Management-Systems-CMS/Kooboo/Microsoft/Data/Extensions/DataExtensions.cs.htm

然后只需将您的位置更改为:

return this.ObjectContext.EventLog.Where(InvocationExpander.Expand(bounds));

关于c# - "Or"Together Expression<Func<EntityFramework Entity, bool>> in .NET 4, Silverlight RIA 域服务,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3993111/

相关文章:

c# - 在 C# 中获取实际日期时间而不是系统日期时间

silverlight - 为什么我的 Silverlight 应用程序使用如此多的非托管内存?

c# - Linq - 从字典中获取所有键,其中值列表中的所有值都等于条件

linq - 是否可以在没有LINQ的情况下使用 Entity Framework ?

c# - 使用数据库日期时间

c# - IBM MQSeries 从 .NET 访问问题

c# - 获取数组中的最后一个数字(输入和输出)C#

c# - 是否有 "stock"空闲/等待对话框?

xaml - 如何获取项目控件中项目的索引

wcf - 将 ClaimCollection 从 Silverlight 发送到 WCF