SQL объединяет запрос в одну строку с двумя отфильтрованными столбцами - PullRequest
0 голосов
/ 17 сентября 2018

Я использую WorldWideImporters примеры таблиц базы данных Microsoft.Я пытаюсь вернуть строки, являющиеся клиентами, со столбцами, в которых будут показаны их общие продажи за 2014, 2015 гг., А также итоговые суммы по два в каждом из них.Мне не разрешено использовать subqueries любого рода.

Для этой проблемы я пытаюсь решить ее следующим образом:

SELECT C.CustomerID
      ,C.CustomerName
      ,ISNULL(SUM(OL.Quantity * OL.UnitPrice), 0.00) AS [2014Sales]
      ,ISNULL(SUM(OLP.Quantity * OLP.UnitPrice), 0.00) AS [2015Sales]
      ,ISNULL(SUM(OL.Quantity * OL.UnitPrice), 0.00)
       + ISNULL(SUM(OLP.Quantity * OLP.UnitPrice), 0.00) AS [TotalSales]
FROM Sales.Customers AS C 
LEFT OUTER JOIN Sales.Orders AS O ON C.CustomerID = O.CustomerID
AND O.OrderDate BETWEEN '2014-01-01' AND '2014-12-31'
LEFT OUTER JOIN Sales.OrderLines AS OL ON O.OrderID = OL.OrderID
LEFT OUTER JOIN Sales.Orders AS OP ON O.CustomerID = C.CustomerID
AND O.OrderDate BETWEEN '2015-01-01' AND '2015-12-31'
LEFT OUTER JOIN Sales.OrderLines AS OLP ON OL.OrderID = O.OrderID
GROUP BY C.CustomerID
        ,C.CustomerName
ORDER BY TotalSales DESC, CustomerID;

У меня возникают трудности с пониманием соединений.Я пришел из-за некоторого объектно-ориентированного опыта, и я не могу полностью сосредоточиться на реляционных соединениях.Я вижу, как можно решить эту проблему с помощью подзапросов, один для 2015 года, один для 2014 года.

В моем нынешнем виде мой запрос выполняется бесконечно, а это значит, что способ, которым я пытался объединиться дважды, должен пытаться объединить тожемного комбинаций рядов.Любая помощь, объясняющая, что здесь происходит и как исправить мой запрос, будет очень признательна.

1 Ответ

0 голосов
/ 17 сентября 2018

При редактировании запроса есть строки, которые не имеют смысла:

Вы присоединились к одним и тем же таблицам, не указав в условии ON их состояние.

Обратите внимание, что вы назвали Sales.Orders и Sales.OrderLines OP и OLP соответственно, но все еще используете критерии O.CustomerID = C.CustomerID и OL.OrderID = O.OrderID.

LEFT OUTER JOIN Sales.OrderLines AS OL ON O.OrderID = OL.OrderID
LEFT OUTER JOIN Sales.Orders AS OP ON O.CustomerID = C.CustomerID
AND O.OrderDate BETWEEN '2015-01-01' AND '2015-12-31'
LEFT OUTER JOIN Sales.OrderLines AS OLP ON OL.OrderID = O.OrderID

Посмотрите, работает ли это: я только исправил ваши критерии соединения.

SELECT C.CustomerID
      ,C.CustomerName
      ,ISNULL(SUM(OL.Quantity * OL.UnitPrice), 0.00) AS [2014Sales]
      ,ISNULL(SUM(OLP.Quantity * OLP.UnitPrice), 0.00) AS [2015Sales]
      ,ISNULL(SUM(OL.Quantity * OL.UnitPrice), 0.00)
       + ISNULL(SUM(OLP.Quantity * OLP.UnitPrice), 0.00) AS [TotalSales]
FROM Sales.Customers AS C 
LEFT OUTER JOIN Sales.Orders AS O ON C.CustomerID = O.CustomerID
                                  AND CONVERT(date, O.OrderDate) BETWEEN '2014-01-01' AND '2014-12-31'
LEFT OUTER JOIN Sales.OrderLines AS OL ON O.OrderID = OL.OrderID
LEFT OUTER JOIN Sales.Orders AS OP ON C.CustomerID = OP.CustomerID
                                   AND CONVERT(date, OP.OrderDate) BETWEEN '2015-01-01' AND '2015-12-31'
LEFT OUTER JOIN Sales.OrderLines AS OLP ON OP.OrderID = OLP.OrderID 
GROUP BY C.CustomerID
        ,C.CustomerName
ORDER BY [TotalSales] DESC, CustomerID;

Я также добавил CONVERT(date в поле даты, чтобы игнорировать часть времени.

EDIT:

Без использования subquery Я думаю, это не сработает. Поэтому я просто оставлю это здесь, на случай, если вы уже сможете его использовать.

SELECT [2014].CustomerID
      ,[2014].CustomerName
      ,[2014Sales]
      ,[2015Sales]
      ,[2014Sales] + [2015Sales] AS [TotalSales]
FROM (
    (SELECT C.CustomerID
           ,C.CustomerName
           ,ISNULL(SUM(OL.Quantity * OL.UnitPrice), 0.00) AS [2014Sales]
     FROM Sales.Customers AS C 
     LEFT OUTER JOIN Sales.Orders AS O ON C.CustomerID = O.CustomerID
     LEFT OUTER JOIN Sales.OrderLines AS OL ON O.OrderID = OL.OrderID
     WHERE O.OrderDate BETWEEN '2014-01-01' AND '2014-12-31'
     GROUP BY C.CustomerID
             ,C.CustomerName) AS [2014]
LEFT OUTER JOIN
    (SELECT C2.CustomerID
           ,C2.CustomerName
           ,ISNULL(SUM(OLP.Quantity * OLP.UnitPrice), 0.00) AS [2015Sales]
     FROM Sales.Customers AS C2
     LEFT OUTER JOIN Sales.Orders AS OP ON OP.CustomerID = C2.CustomerID
     LEFT OUTER JOIN Sales.OrderLines AS OLP ON OP.OrderID = OLP.OrderID
     WHERE OP.OrderDate BETWEEN '2015-01-01' AND '2015-12-31'
     GROUP BY C2.CustomerID
             ,C2.CustomerName) AS [2015] ON [2014].CustomerID = [2015].CustomerId
ORDER BY [2014Sales] + [2015Sales] DESC, CustomerID;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...