我正在尝试使用少量一致的GroupJoin编写ObjectQuery,这意味着应该有一个主表选择+几个额外的LEFT JOIN。我正在使用SelectMany方法执行以下操作,因为没有它我无法访问字段RoleID:
var routesQuery = entities.Routes.Join(
entities.Locales,
Routes => Routes.LocaleID,
Locales => Locales.LocaleID,
(Routes, Locales) => new { Routes = Routes }
).GroupJoin(
entities.LinkRolesPermissions,
Routes => Routes.Routes.RouteID,
LinkRolesPermissions => LinkRolesPermissions.EntityID,
(Routes, LinkRolesPermissions) => new
{
LinkRolesPermissions = LinkRolesPermissions,
RoleID = LinkRolesPermissions.SelectMany(
LRS => LRS.RoleID,
(LRS, RoleID) => new { RoleID = LRS.RoleID }
)
}
)
.SelectMany(
LinkRolesPermissions => LinkRolesPermissions.RoleID,
(LinkRolesPermissions, RoleID) => new { RoleID = RoleID }
).GroupJoin(
entities.aspnet_Roles,
LRS => LRS.RoleID,
RLS => RLS.RoleId,
(LRS, RLS) => new { LRS = LRS }
);
一切正常,但它以某种方式作为INNER JOIN工作,我意识到SelectMany方法会导致这种行为。它会生成此查询:
SELECT 1 AS [C1], 1 AS [C2], [Extent3].[RoleID] AS [RoleID] FROM [dbo].[Routes] AS [Extent1]
INNER JOIN [dbo].[Locales] AS [Extent2] ON ([Extent1].[LocaleID] = [Extent2].[LocaleID]) OR (([Extent1].[LocaleID] IS NULL) AND ([Extent2].[LocaleID] IS NULL))
INNER JOIN [dbo].[LinkRolesPermissions] AS [Extent3] ON ([Extent1].[RouteID] = [Extent3].[EntityID]) OR (([Extent1].[RouteID] IS NULL) AND ([Extent3].[EntityID] IS NULL))
我将其删除并收到以下错误:
var routesQuery = entities.Routes.Join(
entities.Locales,
Routes => Routes.LocaleID,
Locales => Locales.LocaleID,
(Routes, Locales) => new { Routes = Routes }
).GroupJoin(
entities.LinkRolesPermissions,
Routes => Routes.Routes.RouteID,
LinkRolesPermissions => LinkRolesPermissions.EntityID,
(Routes, LinkRolesPermissions) => new
{
LinkRolesPermissions = LinkRolesPermissions,
RoleID = LinkRolesPermissions.SelectMany(
LRS => LRS.RoleID,
(LRS, RoleID) => new { RoleID = LRS.RoleID }
)
}
)
.GroupJoin(
entities.aspnet_Roles,
LRS => LRS.RoleID,
RLS => RLS.RoleId,
(LRS, RLS) => new { LRS = LRS }
);
方法的类型参数 “System.Linq.Enumerable.SelectMany(System.Collections.Generic.IEnumerable, System.Func>中 System.Func)” 无法从使用中推断出来。尝试 指定类型参数 明确。
请有人向我解释这种行为,如果可能的话,建议如何解决这个问题。
提前致谢。
答案 0 :(得分:1)
您正试图急切地加载相关对象。使用Include方法执行此操作。
http://msdn.microsoft.com/en-us/library/bb896272.aspx
IQueryable<Route> query =
from route in entities.Routes.Include("LinkRolesPermissions.aspnet_Roles")
where route.Locales.Any()
select route;
为此,您必须设置导航属性。
http://msdn.microsoft.com/en-us/library/bb738520.aspx
PS:您不必每次都投射到匿名类型:
(Routes, Locales) => new { Routes = Routes }
可能是
(Routes, Locales) => Routes
答案 1 :(得分:0)
好吧,继续折磨LINQ可能会有用,虽然现在它似乎没用,LINQ可能只适用于包含一个表的短查询。它是为数组和XML,IMO创建的。
对于真正的 SQL查询,使用在EF实体中初始化的直接SQL查询会更好,如下所示:
ObjectQuery<DbDataRecord> query = new ObjectQuery<DbDataRecord>
(
"SELECT c.Name,c.City, d.Name FROM ContosoEntities.Customer as c " +
"LEFT JOIN ContosoEntities.Products as d ON d.Name = c.Name " +
"WHERE c.Country=@ctry", ent
);
query.Parameters.Add(new ObjectParameter("ctry", "Australia"));
此处列出的所有EF变体使用: