我有3个表:Principal(Principal_ID,Scale),Frequency(Frequency_ID,Value)和Visit(Visit_ID,Principal_ID,Frequency_ID)。 我需要一个返回所有主体的查询(在Principal表中),并且对于每条记录,查询该主体所需的容量,计算如下:
Capacity = (Principal.Scale == 0 ? 0 : (Frequency.Value == 1 ? 1 : Frequency.Value * 1.8) / Principal.Scale)
我正在使用LINQ to SQL,所以这是查询:
from Principal p in ShopManagerDataContext.Instance.Principals
let cap =
(
from Visit v in p.Visits
let fqv = v.Frequency.Value
select (p.Scale != 0 ? ((fqv == 1.0f ? fqv : fqv * 1.8f) / p.Scale) : 0)
).Sum()
select new
{
p,
Capacity = cap
};
生成的TSQL:
SELECT [t0].[Principal_ID], [t0].[Name], [t0].[Scale], (
SELECT SUM(
(CASE
WHEN [t0].[Scale] <> @p0 THEN (
(CASE
WHEN [t2].[Value] = @p1 THEN [t2].[Value]
ELSE [t2].[Value] * @p2
END)) / (CONVERT(Real,[t0].[Scale]))
ELSE @p3
END))
FROM [Visit] AS [t1]
INNER JOIN [Frequency] AS [t2] ON [t2].[Frequency_ID] = [t1].[Frequency_ID]
WHERE [t1].[Principal_ID] = [t0].[Principal_ID]
) AS [Capacity]
FROM [Principal] AS [t0]
我得到的错误:
SqlException: Multiple columns are specified in an aggregated expression containing an outer reference. If an expression being aggregated contains an outer reference, then that outer reference must be the only column referenced in the expression.
想法如何在一个查询中解决这个问题?
非常感谢你!
答案 0 :(得分:1)
通过更改方法,有以下两种方法:
答案 1 :(得分:1)
根据评论,我有另一个建议。由于您的错误来自SQL,并且您没有使用新列作为过滤器,因此您可以将计算移动到客户端。为此,您需要提取所有相关记录(在您的上下文中使用DataLoadOptions.LoadWith&lt;&gt;)。
为了进一步使用绑定到DataGrid的愿望,将复杂性埋没在Principal的属性中可能是最容易的。
partial class Principal
{
public decimal Capacity
{
get
{
return this.Scale == 0 ? 0 : this.Visits.Select(v =>
(v.Frequency.Value == 1 ? 1 : v.Frequency.Value * 1.8) / this.Scale).Sum();
}
}
}
然后您的检索真的简单:
using (ShopManagerDataContext context = new ShopManagerDataContext())
{
DataLoadOptions options = new DataLoadOptions();
options.LoadWith<Principal>(p => p.Visits);
options.LoadWith<Visit>(v => v.Frequency);
context.LoadOptions = options;
return (from p in context.Principals
select p).ToList();
}