通用类型T作为变量名称

时间:2015-01-23 09:43:09

标签: c# entity-framework generics

我正在使用EntityFramework,我需要一些方法来将实体的传入列表与数据库同步(覆盖记录描述或将它们标记为过时):

    public void Synchronize<T>(List<T> entityList)
    {
        //do something
    }

首先,我需要从相应的表中获取所有数据并获得两个列表之间的差异(一个不可更改的东西是条目的GUID)。 例如,如果传入的entityList的类型是User,那么我需要从“User”表等获取所有数据。

不起作用:

        var query = from entity in typeof(T)
                    select entity;

当然,我可以用旧的方式做到:

switch (typeof(T).Name)
        { 
            case "User":
                var query = from user in User
                            select user;
                //Sync with User table
                break;
            case "Project":
                var query = from project in Project 
                            select project ;
                //Sync with Project table
                break;
        }

但也许有一种优雅的方式来处理通用?因为我有很多表要同步。谢谢!

3 个答案:

答案 0 :(得分:5)

如果您有权访问DbContext,则可以使用方法Set<T>来执行此操作。

var query = from entity in context.Set<T>() select entity;

但要使其在您的上下文中工作,您必须至少对类型T施加约束,并且实体需要共享类型或接口。否则你无法建立你的查询,因为T可以是任何东西(object)。

答案 1 :(得分:2)

您滥用泛型用于非通用的东西。也许您的代码的某些部分是通用的,但您应该在另一种方法中拆分该代码。

您可以使用界面抽象出一些功能,但基本上答案是:您不应该这样做。

答案 2 :(得分:0)

如果你可以使用ObjectContext,你可以这样做:

var octx = (ctx as IObjectContextAdapter).ObjectContext;
var query = octx.CreateQuery<T>("SELECT VALUE v FROM " + typeof(T).Name + " AS v");
var result = query.ToList();

在此处查看有关CreateQuery的更多信息:https://msdn.microsoft.com/en-us/library/bb339670(v=vs.110).aspx