我有一个查询:
model.Queue = _db.Orders
.Join(_db.Tool,
a => a.PART_KEY,
b => b.PART_KEY,
(a, b) => new { a, b })
.Where(r => (r.a.PART_KEY == r.b.PART_KEY) && (r.b.Site == Site))
.Where(r => (r.a.Start > 0) && (r.a.Finish == 0))
.GroupBy(r => new { r.a.GROUP })
.Select(r => new Queue
{
name = r.Key.GROUP,
count = r.GroupBy(g => g.a.PART_KEY).Count(),
average = r.Average(g => g.a.DaysInSequence)
});
查询当前用于为用户生成度量。用户现在希望将度量标准扩展到包含表OrdersCompleted
中已完成的订单。在数据库中,当一个订单完成时,整个订单从Orders
移动到OrdersComplete
。两个表具有相同的结构,即相同的列和相同的模型类。
看起来我需要使用的扩展方法是Concat
,但是我在弄清楚语法以使其与此特定查询一起工作时遇到了问题。似乎添加.Concat(_db.OrdersComplete)
作为第一个扩展方法应该工作,但情况似乎并非如此。
问题是,即使这两个表具有具有完全相同类型和名称的完全相同的列,生成类的工具也会创建具有不同名称的两种类型。由于类型与不完全相同,因此Concat
将不起作用。您需要做一些事情来映射一个或两个表,以便它们共享一个类型。
一种选择是将它们都映射到一个匿名类型。添加如下内容:
.Select(o => new
{
o.PART_KEY,
o.GROUP
//Any other columns you need from each order
});
在_db.Orders
和_db.OrdersComplete
之后。然后Concat
将工作。
如果您认为需要处理所有组合顺序是常见的,那么另一个选项是解决DB类不相关的潜在问题。您可以修改实际的DB对象,以便在所有查询中更容易地执行此操作。
一种选择是创建两个类都可以扩展/实现的接口或基类型。如果您创建了包含这两种类型共享的所有列的接口,并让它们都实现该接口,那么您可以使用Concat
创建该接口的枚举。(我不确定这对Linq-To-Sql有多好)
第三种选择是在数据库中创建一个视图,在底层,它只是这两个表上的Union All
,可能从一个或两个表中提取列的子集。然后,您可以从该视图查询,而不是自己连接表。
Servy的答案是正确的:最简单的方法就是从两个查询中分别创建一个匿名类。只要匿名类具有相同的属性,Concat
和Union
都可以工作。
一种可能的替代方法是在两个表上运行相同的查询(因为您已经将结果投影到一个新的Queue
对象中,并将两个查询的结果投影到Concat
中)。