2014-03-27 3 views
-1

Я новичок в SQL ...SQL Server; пытаясь объединить три таблицы, агрегировать и группа результатов

Я работаю со следующими тремя столами:

Таблица: Кампании

Campaign SourcePhone StartDate EndDate 
A   1112223333 20140303 20140309 
B   2223334444 20140303 20140309 
C   1112223333 20140310 20140316 
D   3334445555 20140217 20150217 

Таблица: PhoneMapping (сопоставление SourcePhone из кампании в таблицу заказов)

SourcePhone TransferToPhone 
1112223333 9998887777 
1112223333 8887776666 
2223334444 7776665555 
3334445555 6665554444 
3334445555 5554443333 

Таблица: Заказы

Date  TransferToPhone Orders 
20140304 9998887777  3 
20140304 8887776666  4 
20140304 6665554444  34 
20140305 7776665555  7 
20140305 9998887777  5 
20140306 9998887777  10 
20140306 8887776666  13 
20140307 8887776666  7 
20140309 7776665555  1 
20140311 9998887777  35 
20140313 8887776666  8 
20140315 9998887777  22 
20140305 6665554444  11 

Я пытался придумать запрос, который будет соединить эти три таблицы и предоставить результаты ниже. По сути, мне нужно придумать сумму TotalOrders для каждой кампании, SourcePhone #, Transfer to phone # и диапазона дат (между StartDate и EndDate для каждой кампании). Ниже приведены результаты, которые я ожидаю от запроса (я думаю, что правильно сделал математику). Любая помощь очень ценится!

Ожидаемые результаты:

Campaign SourcePhone TransferToPhone StartDate EndDate  TotalOrders 
A   1112223333 9998887777  20140303 20140309 18 
A   1112223333 8887776666  20140303 20140309 24 
B   2223334444 7776665555  20140303 20140309 8 
C   1112223333 9998887777  20140310 20140316 57 
C   1112223333 8887776666  20140310 20140316 8 
D   3334445555 6665554444  20140217 20150217 45 

Вот что я пытался, но он не группирует данные, основанные на диапазоне дат:

SELECT C.Campaign, C.SourcePhone, PM.TransferToPhone, C.StartDate , C.EndDate, O.TotalOrders 
FROM Campaigns AS C 
    INNER JOIN 
     (SELECT SourcePhone, TransferToPhone 
      FROM   PhoneMapping 
      WHERE  (TransferToPhone IS NOT NULL)) AS PM ON C.SourcePhone = PM.SourcePhone 
      INNER JOIN 
      (SELECT  TransferToPhone, SUM(Orders) AS TotalOrders 
       FROM   Orders 
       WHERE  (Orders IS NOT NULL) 
       Group by TransferToPhone) AS O ON PM.TransferToPhone = O.TransferToPhone 

GROUP BY C.Campaign, C.SourcePhone, PM.TransferToPhone, C.StartDate , C.EndDate 
+1

MySQL или Microsoft? пожалуйста, исправьте свои теги. Также обратите внимание на теги JOIN. –

+1

Какая СУРБД и один из них предоставляют надлежащие DDL (и/или sqlfiddle) ВМЕСТЕ С ЖЕСТКОЙ РЕЗУЛЬТАТОМ. Также покажите нам, что вы что-то пробовали. – Strawberry

+0

Спасибо за ваши комментарии. Теги были обновлены, и запрос, который я пытался воспроизвести, был опубликован. – user3469435

ответ

1

ли это получить, что вам нужно?

SELECT C.Campaign, 
     C.SourcePhone, 
     P.TransferToPhone, 
     C.StartDate, 
     C.EndDate, 
     SUM(O.TotalOrders) 
FROM Campaigns C 
    JOIN PhoneMapping P 
    ON C.SourcePhone = P.SourcePhone 
    JOIN Orders O 
    ON O.TransferToPhone = P.TransferToPhone 
GROUP BY C.Campaign, C.StartDate, C.EndDate, P.SourcePhone, P.TransferToPhone 
+3

Следует отметить, что, как правило, все таблицы должны иметь уникальный идентификатор. И другие таблицы должны связываться с этими ключами. Поэтому вместо сопоставления на SourcePhone и TransferPhone здесь вы должны использовать что-то вроде CampaignID, PhoneMappingID и OrderID. –

+0

Согласовано, что поможет точно идентифицировать уникальные записи и улучшить нормализацию, так как больше не будет необходимости дублировать SourcePhone и TransferToPhone. –

+0

Не говоря уже о том, что база данных намного проще индексировать и, таким образом, увеличивает производительность приложений с течением времени по мере роста записей в базе данных. –