[英]Linq to Entities Where In Clause Many to Many
我正在尝试使用Where In子句来与linq一起使用到实体,并遇到了问题。 我的问题是我有多个不同实体的列表,我想从这些列表中选择一组Game实体,实际上是为它们设置了SQL WHERE IN子句。 问题是实体列表正在与具有多对多关系的游戏实体的相关实体进行比较。 我已经做了很多研究,并尝试了很多解决方案来解决这个问题,但只是做得还不够,我真的很感谢stackoverflow社区的一些帮助。
提前致谢。
编辑:
我尝试这样做,而不是工会:
var relatedGames = from game in ugdb.Games
where game.Developers.Any(d => relatedDevelopers.Any(r => r.DeveloperID == d.DeveloperID))
|| game.Publishers.Any(d => relatedPublishers.Any(r => r.PublisherID == d.PublisherID))
|| game.Genres.Any(d => relatedGenres.Any(r => r.GenreID == d.GenreID))
select game;
通过这两个联合,我收到以下错误消息:
base {System.SystemException} = {“无法创建类型为'UltimateGameDB.Domain.Entities.Developer'的常量值。在此上下文中仅支持基本类型(例如Int32,String和Guid')。
有谁知道如何去做,而没有
我当前的代码:
public IQueryable<Video> GetSimilarVideos(Guid videoId)
{
IQueryable<Video> result = null;
List<Video> similarVideoList = null;
Video currentVideo = ugdb.Videos.Find(videoId);
List<Genre> relatedGenres = new List<Genre>();
List<Developer> relatedDevelopers = new List<Developer>();
List<Publisher> relatedPublishers = new List<Publisher>();
foreach (var game in currentVideo.Games)
{
relatedDevelopers.AddRange(game.Developers);
relatedPublishers.AddRange(game.Publishers);
relatedGenres.AddRange(game.Genres);
}
relatedDevelopers = relatedDevelopers.Distinct().ToList<Developer>();
relatedPublishers = relatedPublishers.Distinct().ToList<Publisher>();
relatedGenres = relatedGenres.Distinct().ToList<Genre>();
//This is the piece I am having trouble with!
var relatedGames = from game in ugdb.Games
where game.Developers.Union(relatedDevelopers).Count() > 0
|| game.Genres.Union(relatedGenres).Count() > 0
|| game.Publishers.Union(relatedPublishers).Count() > 0
select game;
foreach (var game in relatedGames)
{
similarVideoList.AddRange(game.Videos.Where(v => v.VideoType.Equals(currentVideo.VideoType)));
}
result = similarVideoList.Distinct().AsQueryable<Video>();
return result;
}
您不能传递本地实体-在您的情况下,它们将不会转换为sql,这是relatedDevelopers。 Linq to Entities没有办法转换relatedDevelopers.Contains
。包含Sql IN
。
您可以强制转换游戏列表并在内存中进行调用,这样就不必将其转换为sql了-这很容易,但是如果您的数据库很大,则可能很难全部加载,只需添加ToList()
在ugdb.Games
结束时
var relatedGames = from game in ugdb.Games.ToList()
where game.Developers.Any(d => relatedDevelopers.Any(r => r.DeveloperID == d.DeveloperID))
|| game.Publishers.Any(d => relatedPublishers.Any(r => r.PublisherID == d.PublisherID))
|| game.Genres.Any(d => relatedGenres.Any(r => r.GenreID == d.GenreID))
select game;
另外,您可以创建一个ID列表并传递它,因为这是SQL可以识别的原始类型:
var relatedDevelopers = currentVideo.Games.SelectMany( g => g.Developers ).Select( g => g.DeveloperID ).ToArray();
var relatedPublishers = currentVideo.Games.SelectMany( g => g.Developers ).Select( g => g.DeveloperID ).ToArray();
var relatedGenres = currentVideo.Games.SelectMany( g => g.Developers ).Select( g => g.DeveloperID ).ToArray();
//This is the piece I am having trouble with!
var relatedGames = from game in ugdb.Games
where game.Developers.Any( d => relatedDevelopers.Contains(d.DeveloperID) )
|| game.Publishers.Any( d => relatedPublishers.Contains(d.PublisherID))
|| game.Genres.Any( d => relatedGenres.Contains(d.GenreID) )
select game;
该模式通常使用嵌套的Any
或带有Contains
的Any
var relatedDeveloperIds = relatedDevelopers.Select(r => r.Id).ToList();
game.Developers.Any(d => relatedDeveloperIds.Contains(d.Id))
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.