Entity Framework - Join to a List

南笙酒味 提交于 2019-12-24 05:09:09

问题


I need to retrieve a list of entities from my database that matches a list of items in a plain list (not EF). Is this possible with Entity Framework 4.1?

Example:

var list = new List<string> { "abc", "def", "ghi" };
var items = from i in context.Items
            where list.Contains(i.Name)
            select i;

This works great to return rows that match one property, but I actually have a more complex property:

var list = new List<Tuple<string, string>>
{
    new Tuple<string,string>("abc", "123"),
    new Tuple<string,string>("def", "456")
};

// i need to write a query something like this:
var items = from i in context.Items
where list.Contains(new Tuple<string,string>(i.Name, i.Type))
select i;

I know that is not valid because it will say it needs to be a primitive type, but is there any way to do what I'm trying to accomplish or will I need to resort to a stored procedure?


回答1:


You have a few options:

1) You could, of course, write a stored procedure to do what you need and call it.

2) You could read the table into memory and then query the in memory list...that way you don't have to use primitives:

var items = from i in context.Items.ToList()
            where list.Contains(new Tuple<string, string>(i.Name, i.Type))
            select i;

3) You could also convert your query to use primitives to achieve the same goal:

var items = from i in context.Items
            join l in list
            on new { i.Name, i.Type } equals 
                new { Name = l.Item1, Type = l.Item2 }
            select i;

I would go with the second option as long as the table isn't extremely large. Otherwise, go with the first.




回答2:


You need to break it down to sub-properties. For example, something like (this might not compile, i'm not able to test at the moment, but it should give you something to work with):

var items = from i in context.Items 
where list.Select(x => x.Item1).Contains(i.Name) 
   && list.Select(x => x.Item2).Contains(i.Type)
select i; 



回答3:


You have to think about what the resulting SQL would look like, this would be difficult to do directly in SQL.

My suggestion would be you split out one field of the tuples and use this to cut down the results list, get back the query result then filter again to match one of the tuples e.g.

var list = new List<string> { "abc", "def" };
var list2 = new List<Tuple<string, string>>
{
  new Tuple<string,string>("abc", "123"),
  new Tuple<string,string>("def", "456")
};
var items = (from i in context.Items
        where list.Contains(i.Name)
        select i)
        .AsEnumerable()
        .Where(i => list2.Any(j => j.val1 == i.Name && j.val2 == i.Type);


来源:https://stackoverflow.com/questions/8053468/entity-framework-join-to-a-list

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!