LINQ:为什么联合的联合会抛出错误消息“IQueryable<...> 不包含‘Union’的定义”?

问题描述 投票:0回答:1

问题是关于 LINQ 中的嵌套联合:我想组合 3 个不同数据库中的表中的数据,并将它们显示在一个结果表中。


为了清楚地说明我想要实现的目标,我将展示如何在 SQL 中完成此操作(我使用的是 Northwind、Nutshell 和 Pubs 数据库,因此您可以更轻松地自行尝试):

SELECT 'Territories' as [Table], TerritoryDescription as Item, RegionID as ID 
  FROM Northwind.dbo.Territories
UNION
SELECT 'MedicalArticles' as [Table], Topic as Item, ID as ID  
  FROM Nutshell.dbo.MedicalArticles
UNION
SELECT 'Authors' as [Table], City as Item, Zip as ID 
  FROM pubs.dbo.Authors

底层表结构为: table structure 该查询工作正常,没有错误,并返回一个包含 3 列(表、项目和 ID)的表,组合了来自 3 个表 Territories、MedicalArticles 和 Authors 的数据:

Result

如果您向 3 个 select 语句中的每一个添加

top 3
,您将得到:

ResultTop3


现在我在 LINQ 中尝试了同样的方法,编写如下代码:

void Main()
{
    // In LinqPad:
    // Drag + Drop databases from Schema explorer to code window with pressed Ctrl key
    var dc = this; // database context: Northwind + Nutshell + pubs

    // first database Northwind is default
    var q1 = (from s in dc.Territories select new { Table = "Territories", 
                Item = s.TerritoryDescription, ID = s.RegionID }).Distinct().Take(5); 

    // second database .Nutshell needs to be referenced
    var q2 = (from s in dc.Nutshell.MedicalArticles select new { Table="MedicalArticles", 
                Item = s.Topic, ID=s.ID }).Distinct().Take(5); 

    // third database .Pubs needs to be referenced
    var q3 = (from s in dc.Pubs.Authors select new { Table = "Authors", 
                Item = s.City, ID = s.Zip }).Distinct().Take(5); 

    // union q1 with q2 works
    var u1 = q1.Union(q2.Select(s => s)); u1.Dump();

    // but union u1 with q3 does not work
    //var u2 = u1.Union(q3.Select(s => s)); u2.Dump();      
}

第一个联合(q1 与 q2)工作正常 - 但我无法将第三个查询 q3 应用于结果(即

u1.Union(q3.Select(s => s))
不起作用)。

当我取消注释查询 u2 的行时收到的错误消息不是很有帮助:

CS1929 'IQueryable<<anonymous type: string Table, string Item, int ID>>' does not contain a definition for 'Union' and the best extension method overload 'ParallelEnumerable.Union<<anonymous type: string Table, string Item, string ID>>(ParallelQuery<<anonymous type: string Table, string Item, string ID>>, IEnumerable<<anonymous type: string Table, string Item, string ID>>)' requires a receiver of type 'ParallelQuery<<anonymous type: string Table, string Item, string ID>>'

如何修复错误?


注意: 上面的例子可以在LinqPad中尝试。只需将代码放在一个窗口中,然后按住 Ctrl 键添加 3 个数据库 Northwind、NutShell 和 Pubs,然后将数据库拖放到查询窗口即可。

c# .net sql-server entity-framework linq
1个回答
4
投票

非常感谢所有在评论中做出贡献的人! 我根据 Ivansgmoore 的评论创建了这个答案:

“匿名类型投影中

ID
属性的类型很可能不同。检查
RegionID
Zip
的类型。”
- Ivan

“错误消息显示

Zip
是字符串,而
RegionID
是整数。解决方法是将
ID = s.RegionID
更改为
ID = s.RegionID.ToString()
,将
ID=s.ID
更改为
ID=s.ID.ToString()
。”
- 斯格摩尔

这绝对是解决方案。看起来,C# 中的类型检查比 SQL 中更严格(回顾一下,在 SQL 中,联合工作无需任何额外的类型转换)。

但是错误消息肯定具有误导性(“IQueryable <>”不包含“Union”的定义”),这就是提出问题的原因。更有意义的错误消息在这里会很有帮助。

© www.soinside.com 2019 - 2024. All rights reserved.