gpt4 book ai didi

linq - 亚音速 3.0 和 linq

转载 作者:行者123 更新时间:2023-12-01 04:31:57 26 4
gpt4 key购买 nike

我正在玩弄 Subsonic 3.0 SimpleRepository 并尝试使用一个 linq 查询获取菜单和菜单项,但菜单项始终为空

菜单

public class Menu
{
public Menu()
{
MenuId = 0;
MenuName = "";
MenuItems = null;
}
public int MenuId { get; set; }
public string MenuName { get; set; }
public MenuItem MenuItems { get; set; }
}

菜单项

public class MenuItem
{
public MenuItem()
{
MenuItemId = 0;
MenuId = 0;
MenuItemName = "";
}
public int MenuItemId { get; set; }
public int MenuId { get; set; }
public string MenuItemName { get; set; }
}

Linq 查询

var menus =  from m in _repo.All<Menu>()
from mi in _repo.All<MenuItem>()
where m.MenuItems.MenuItemId == mi.MenuItemId
select new Menu
{
MenuId = m.MenuId,
MenuName = m.MenuName,
MenuItems = {
MenuItemId = mi.MenuItemId,
MenuItemName = mi.MenuItemName
}
};

有人能告诉我我做错了什么吗?

最佳答案

我想我已经找到了这个问题的实际答案。我一直在 SubSonic 源代码中翻找,发现在将数据读取器映射到对象时使用了两种类型的对象投影:一种用于匿名类型和分组,另一种用于其他所有类型:

这是一个片段:SubSonic.Linq.Structure.DbQueryProvider 的第 269 - 298 行

IEnumerable<T> result;
Type type = typeof (T);
//this is so hacky - the issue is that the Projector below uses Expression.Convert, which is a bottleneck
//it's about 10x slower than our ToEnumerable. Our ToEnumerable, however, stumbles on Anon types and groupings
//since it doesn't know how to instantiate them (I tried - not smart enough). So we do some trickery here.
if (type.Name.Contains("AnonymousType") || type.Name.StartsWith("Grouping`") || type.FullName.StartsWith("System.")) {
var reader = _provider.ExecuteReader(cmd);
result = Project(reader, query.Projector);
} else
{
using (var reader = _provider.ExecuteReader(cmd))
{
//use our reader stuff
//thanks to Pascal LaCroix for the help here...
var resultType = typeof (T);
if (resultType.IsValueType)
{
result = reader.ToEnumerableValueType<T>();
}
else
{
result = reader.ToEnumerable<T>();
}
}
}
return result;

事实证明,SubSonic ToEnumerable 试图将数据读取器中的列名称与您要投影到的对象中的属性相匹配。来 self 的 Linq 的 SQL 查询如下所示:

SELECT [t0].[Id], [t0].[ProductId], [t0].[ReleaseDate], [t0].[ReleasedBy], [t0].[ReleaseNumber], [t0].[RevisionNumber], [t0].[c0]
FROM (
SELECT [t1].[Id], [t1].[ProductId], [t1].[ReleaseDate], [t1].[ReleasedBy], [t1].[ReleaseNumber], [t1].[RevisionNumber], (
SELECT COUNT(*)
FROM [dbo].[Install] AS t2
WHERE ([t2].[ReleaseId] = [t1].[Id])
) AS c0
FROM [dbo].[Release] AS t1
) AS t0
WHERE ([t0].[ProductId] = 2)

请注意 [t0].[c0] 与我的属性名称 NumberOfInstalls 不同。所以 c0 的值永远不会转换到我的对象中。

修复:您只需删除 if 语句并使用慢 10 倍的投影,一切都会正常进行。

关于linq - 亚音速 3.0 和 linq,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1655354/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com