Предположим, у меня есть следующая таблица в моей базе данных SQL Server (2012):
tbl1:
Id1: Id2: Date: Value:
1 A '2018-01-01' 1
1 B '2018-01-01' 1
1 C '2018-01-01' 1
1 A '2018-01-02' 1
1 B '2018-01-02' 1
1 A '2018-01-31' 1
И я хочу получить среднее значение Value
за Id2
, где Id1 = 1
для Date BETWEEN '2018-01-01' AND '2018-01-02'
.
ОДНАКО , в среднем, я хочу разделить на общее количество Date
с, НЕ ТОЛЬКО ДЛЯ ЭТОГО Id2
.
Итак, мой набор результатов будет:
Id2: AvgVal:
A 1+1 / 2 = 1
B 1+1 / 2 = 1
C 1 / 2 = 0.5
Обратите внимание, что значение C делится на 2, хотя в этом диапазоне дат есть только 1 значение для C (другими словами, мы делим только на COUNT(DISTINCT Date) OVER (PARTITION BY Id1)
. Не добавляем дополнительную группировку на Id2
.
Я придумал способ сделать это, используя CTE, и могу придумать способ сделать это, сохраняя делитель во временной переменной, но я ДЕЙСТВИТЕЛЬНО пытаюсь продумать, есть ли способ сделать это в одном операторе SELECT.
Мое текущее решение выглядит следующим образом:
DECLARE @StartDate DATE = '2018-01-01', @EndDate DATE = '2018-01-02', @Id1 INT = 1;
DECLARE @Tbl1 TABLE ([Id1] INT, [Id2] VARCHAR(1), [Date] DATE, [Value] FLOAT);
INSERT INTO @Tbl1 (Id1, Id2, Date, Value)
VALUES
(1, 'A','2018-01-01', 1),
(1, 'B','2018-01-01', 1),
(1, 'C','2018-01-01', 1),
(1, 'A','2018-01-02', 1),
(1, 'B','2018-01-02', 1),
(1, 'A','2018-01-31', 1)
;
WITH CTE AS
(
SELECT *
FROM @Tbl1
WHERE [Date] BETWEEN @StartDate AND @EndDate
AND Id1 = @Id1
),
CTE1 AS
(
SELECT COUNT(DISTINCT [Date]) AS MaxNumDates FROM CTE
)
SELECT
Id2
,SUM(Value) / MaxNumDates AS AvgVal
FROM
CTE
JOIN CTE1
ON 1 = 1
GROUP BY
Id2,
MaxNumDates
И, как я уже сказал, я думаю, что я мог бы также сделать это, присвоив локальной переменной значение MaxNumDates
, но я действительно пытаюсь увидеть, есть ли способ сделать это с помощью одного запроса с некоторыми форма разбиения / агрегации - при условии, конечно, это лучший способ сделать это.
Есть мысли?
Спасибо!