Sql 将“联合所有”与“分组”相结合
在这个问题上,我真的需要一些帮助 我有一张产品表 和一个事务表 和一个CCTransactions表 我需要一个查询,该查询可以联合所有在给定日期范围内的事务和CCTransactions,然后将它们分组为Product.Id、Product.Title、SUMQuantity和SUMTotalAmount 以下是我到目前为止的情况。它不会编译,但我会包括在内,因为人们通常希望看到你尝试过什么。它告诉我: Msg 8120,16级,状态1,第5行 列“Products.Id”在选择列表中无效,因为它未包含在聚合函数或GROUP BY子句中。 Msg 209,16级,状态1,第14行 列名称“Id”不明确 我理解这些错误,但不确定修复它们的最佳方法。在我加入工会之前,这个问题似乎起了作用Sql 将“联合所有”与“分组”相结合,sql,sql-server,Sql,Sql Server,在这个问题上,我真的需要一些帮助 我有一张产品表 和一个事务表 和一个CCTransactions表 我需要一个查询,该查询可以联合所有在给定日期范围内的事务和CCTransactions,然后将它们分组为Product.Id、Product.Title、SUMQuantity和SUMTotalAmount 以下是我到目前为止的情况。它不会编译,但我会包括在内,因为人们通常希望看到你尝试过什么。它告诉我: Msg 8120,16级,状态1,第5行 列“Products.Id”在选择列表中无效,因
DECLARE @dtStart DATE = '2016-08-01';
DECLARE @dtEnd DATE = '2016-08-31';
SELECT p.Id, p.Title, SUM(t.Quantity), SUM(t.TotalAmount) AS Amount
FROM Transactions t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
UNION ALL
SELECT p.Id, p.Title, SUM(t.Quantity), SUM(t.TotalAmount) AS Amount
FROM CCTransactions t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
GROUP BY p.Id, p.Title
ORDER BY Title
您需要两个单独的分组:
或子查询:
SELECT X.id, X.Title, SUM(X.Quantity), SUM(X.TotalAmount)
FROM (
SELECT p.Id, p.Title, t.Quantity, t.TotalAmount
FROM Transactions t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
UNION ALL
SELECT p.Id, p.Title, t.Quantity, t.TotalAmount
FROM CCTransactions t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
) X
GROUP BY X.Id, X.Title
或者您可以重写整个查询:
;WITH
AllTransaction AS
(
SELECT ProductID, Timestamp, Quantity, TotalAmount
FROM Transaction
UNION ALL
SELECT ProductID, Timestamp, Quantity, TotalAmount
FROM CCTransaction
)
SELECT p.Id, p.Ttitle, SUM(t.Quantity), SUM(t.TotalAmount)
FROM AllTransaction t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE @dtStart <= t.[Timestamp] AND t.[TimeStamp] < DATEADD(DAY, 1, @dtEnd)
GROUP BY p.Id, p.Title
关于cast。[TimeStamp]AS DATE的说明首先对2个表使用UNION ALL,并将结果连接到产品:
DECLARE @dtStart DATE = '2016-08-01';
DECLARE @dtEnd DATE = '2016-08-31';
SELECT p.Id, p.Title, SUM(t.Quantity), SUM(t.TotalAmount) AS Amount
FROM (
SELECT ProductId, [TimeStamp], Quantity, TotalAmount FROM Transactions
UNION ALL
SELECT ProductId, [TimeStamp], Quantity, TotalAmount FROM CCTransactions
) t INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
GROUP BY p.Id, p.Title
ORDER BY Title
我喜欢这种方法。我正在确认我是否得到了我期望的数字,我得到了。是的,我喜欢这样的方式:在进行所有额外的联合和分组之前,先获取底层数据。不确定它是否执行得最好,但似乎最容易理解。您也可以尝试应用以下条件:WHERE[TimeStamp]>=@dtStart并将[TimeStamp]强制转换为DATE Yes,这将生成更长的查询。很想知道它对性能的影响。在两个表中的[TimeStamp]上都有索引,这可能会比外部WHERE条件更好。第一个1在联合之前有GROUP BY,与其他2不同。对于AVG,这会产生不同。对于SUM来说,它是否对SUM重要并不重要。对于事务和cctransactions中出现的任何内容,您都将获得具有相同IT、标题组合的多行,因为在进行联合之前,在没有任何聚合的情况下进行分组。您必须进行另一次求和/分组才能再次合并2。
SELECT p.Id, p.Title, SUM(t.Quantity), SUM(t.TotalAmount) AS Amount
FROM Transactions t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
GROUP BY p.Id, p.Title
UNION ALL
SELECT p.Id, p.Title, SUM(t.Quantity), SUM(t.TotalAmount) AS Amount
FROM CCTransactions t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
GROUP BY p.Id, p.Title
SELECT X.id, X.Title, SUM(X.Quantity), SUM(X.TotalAmount)
FROM (
SELECT p.Id, p.Title, t.Quantity, t.TotalAmount
FROM Transactions t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
UNION ALL
SELECT p.Id, p.Title, t.Quantity, t.TotalAmount
FROM CCTransactions t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
) X
GROUP BY X.Id, X.Title
;WITH
AllTransaction AS
(
SELECT ProductID, Timestamp, Quantity, TotalAmount
FROM Transaction
UNION ALL
SELECT ProductID, Timestamp, Quantity, TotalAmount
FROM CCTransaction
)
SELECT p.Id, p.Ttitle, SUM(t.Quantity), SUM(t.TotalAmount)
FROM AllTransaction t
INNER JOIN Products p ON t.ProductId = p.Id
WHERE @dtStart <= t.[Timestamp] AND t.[TimeStamp] < DATEADD(DAY, 1, @dtEnd)
GROUP BY p.Id, p.Title
DECLARE @dtStart DATE = '2016-08-01';
DECLARE @dtEnd DATE = '2016-08-31';
SELECT p.Id, p.Title, SUM(t.Quantity), SUM(t.TotalAmount) AS Amount
FROM (
SELECT ProductId, [TimeStamp], Quantity, TotalAmount FROM Transactions
UNION ALL
SELECT ProductId, [TimeStamp], Quantity, TotalAmount FROM CCTransactions
) t INNER JOIN Products p ON t.ProductId = p.Id
WHERE t.[TimeStamp] >= @dtStart AND CAST(t.[TimeStamp] AS DATE) <= @dtEnd
GROUP BY p.Id, p.Title
ORDER BY Title