简体   繁体   English

C#-如何转换Func <T, bool> 到功能 <dynamic, bool> ?

[英]C# - How to convert Func<T, bool> to Func<dynamic, bool>?

Im using Entity Framework 4, I have an entity 我正在使用实体框架4,我有一个实体

public partial class UserEntity : EntityObject 
{
    public string id_user;
    public string pass;
    public DateTime date_added;
}

and a data transfer object with custom attributes 以及具有自定义属性的数据传输对象

[DataTransferObject("UserEntity")]
public class User
{
    [EntityColumn("id_user")]
    public string idUser { get; set; }
    [EntityColumn("pass")]
    public string password { get; set; }
    [EntityColumn("date_added")]
    public string dateAdded { get; set; }
}

I convert the entity to dto and the dto to entity using these attributes with reflection, I'm using a generic repository for data access methods, when I want to make a query, using Enumerable.Where , to the ObjectSet of the entity, this require a Func<dynamic, bool> (dynamic because the program doesn't know the entity implementing the repository), this works but I want a Func<DTObject, bool> as parameter so I don't have to use entities in business layer, is there a way to achieve something like this? 我使用反射的这些属性将实体转换为dto并将dto转换为实体,当我想使用Enumerable.Where进行查询时,我正在使用通用存储库来访问数据,这是该实体的ObjectSet ,需要一个Func<dynamic, bool> (动态的,因为程序不知道实现存储库的实体),这是Func<DTObject, bool>但是我想要一个Func<DTObject, bool>作为参数,因此我不必在业务层中使用实体,有没有办法实现这样的目标?

public static Func<dynamic, bool> ConvertFunc<DTObject>(Func<DTObject, bool> predicate)
{
    /* do some magic to convert func */
    return newFunc;
}

Func<dynamic, bool> newFunc = ConvertFunc<User>(u => u.idUser == "admin" && u.password == "abc123");
/* newFunc = u => u.id_user == "admin" && u.pass == "abc123" */

I need to stop you right here. 我要在这里阻止你 You are completely wrong on your approach. 您的方法完全错误。 You need to use Queryable.Where<T>(this IQueryable<T> query, Expression<Func<T, bool>>) for EntityFramework to work. 您需要使用Queryable.Where<T>(this IQueryable<T> query, Expression<Func<T, bool>>)使EntityFramework正常工作。 The method you would actually be using is Enumerable.Where<T>(this IEnumerable<T> set, Func<T, bool> predicate) , which would do the filtering IN MEMORY. 您实际使用的方法是Enumerable.Where<T>(this IEnumerable<T> set, Func<T, bool> predicate) ,它将在内存中进行过滤。 This means the road you are going down will download your entire table into memory. 这意味着您要走的路会将整个表下载到内存中。

For this to work you need to be playing with the System.Linq.Expressions namespace. 为此,您需要使用System.Linq.Expressions命名空间。 However, if this is going to work, without some insane amount of logic (more than already exists with Expressions). 但是,如果这行得通,则无需太多疯狂的逻辑(超过Expressions已经存在的逻辑)。 Your Dto signature will be exactly the same as your EntityObject . 您的Dto签名将与EntityObject完全相同。

Given this is true, what value does your DTO add (given the maintenance cost of the class)? 既然如此,DTO会增加什么价值(考虑到该类的维护成本)?

The only value I see is the decoupling of your domain logic from your data storage (ie you don't have EntityObject in your domain layer). 我看到的唯一值是域逻辑与数据存储的解耦(即,域层中没有EntityObject )。 However that problem was solved years ago with POCOs. 但是,几年前,使用POCO解决了该问题。

TLDR TLDR

XY problem. XY问题。 Use POCO instead. 请改用POCO。

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

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