重用LINQ To Entities语句 [英] Reuse a LINQ To Entities statement

查看:73
本文介绍了重用LINQ To Entities语句的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有以下Select表达式将在数据库端执行:

I have the following Select expression that will be performed database-side:

        var model = new ProductListViewModel()
        {
            Products = products
                .Select(q => new ProductViewModel()
                {
                    // Other mapping
                    Name = q.LanguageKey.LanguageValues.FirstOrDefault(p => p.LanguageKeyID == currentLanguageID && p.Active).Value,
                })
                .OrderBy(q => q.Name)
        };

如您所见,名称"部分很长,而我程序的其他部分也使用相同的逻辑.因此,我想重用它(不是整个Select语句,而是Name映射部分).

As you can see, the Name part is quite long, and other part of my program also use the same logic. Therefore, I would like to reuse it (not entire Select statement, just the Name mapping part).

我试图编写仅使用实体的函数:

I tried to write a function that only use the entity:

public static string GetProductName(Product product, int languageID)
{
    return product.LanguageKey.LanguageValues.AsQueryable()
        .FirstOrDefault(q => q.LanguageID == languageID && q.Active).Value;
}

但是,在调用该方法时,我(显然)收到了错误

However, on calling the method, I (obviously) receive the error

LINQ to Entities无法识别方法{X},并且该方法不能转换为商店表达式

LINQ to Entities does not recognize the method {X} method, and this method cannot be translated into a store expression

我搜索了许多关于StackOverflow的文章,但是大多数文章解决了重用整个Select表达式的问题.可以重用吗?还是我必须创建数据库存储过程或函数?

I have searched through many articles on StackOverflow, but most solve the problem of reusing entire Select expression. Is it possible to reuse it? Or do I have to create database Stored Procedure or Function?

推荐答案

一种解决方案是使用 LINQKit .

首先,您需要修改方法以返回这样的表达式:

First, you need to modify your method to return an expression like this:

public Expression<Func<Product, string>> CreateExpression(int languageID)
{
    return product => product.LanguageKey.LanguageValues.AsQueryable()
        .FirstOrDefault(q => q.LanguageID == languageID && q.Active).Value;
}

顺便说一句,我认为您不需要在这里调用.AsQueryable().

By the way, I don't think that you need to invoke .AsQueryable() here.

然后您可以执行以下操作:

Then you can do the following:

var expression = CreateExpression(currentLanguageID);

var model = new ProductListViewModel()
{
    Products = products.AsExpandable()
        .Select(q => new ProductViewModel()
        {
            // Other mapping
            Name = expression.Invoke(q),
        })
        .OrderBy(q => q.Name)
};

注意products变量上的.AsExpandable()调用.

此方法来自LINQKit,它在IQueryable(在您的情况下为products)周围创建包装器,以允许使用lambda表达式内部的表达式.

This method is from LINQKit, and it creates a wrapper around the IQueryable (in your case products) to enable using expressions from inside your lambda expressions.

也请注意,LINQKit也提供了Invoke方法.它允许您在其他表达式(即q => new ProductViewModel(...)中使用expression.

Also notice the Invoke method that is also coming from LINQKit. It allows you to use the expression inside your other expression, i.e., q => new ProductViewModel(....

这篇关于重用LINQ To Entities语句的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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