Агрегатная функция SQL Server без группировки по

#sql #sql-server #sql-server-2012

Вопрос:

Я хочу включить tcon.Inductive_Injection_Hours , tcon.Capacitive_Injection_Hours не применяя group by. Как я могу это сделать?

 SELECT 
    bp.Serial_Number, 
    tcon.Serial_Number AS ConverterSerialNumber, 
    MAX(tcon.Time_Stamp) AS DateStamp,  
    tcon.Inductive_Injection_Hours, 
    tcon.Capacitive_Injection_Hours
FROM 
    dbo.Bypass AS bp 
INNER JOIN 
    dbo.Converter AS c ON bp.Bypass_ID = c.Bypass_ID 
INNER JOIN 
    dbo.Converter_Tel_Data AS tcon ON c.Converter_ID = tcon.Converter_ID
WHERE 
    (bp.Site_ID = 7)
GROUP BY 
    bp.Serial_Number, tcon.Serial_Number, 
    tcon.Inductive_Injection_Hours, tcon.Capacitive_Injection_Hours
ORDER BY 
    ConverterSerialNumber
 

Комментарии:

1. OVER Вместо этого используйте предложение.

2. Что вы имеете в виду под «без применения группового подхода»? Вы хотите агрегировать или нет? Если нет, то чего ты хочешь?

3. предоставьте примерные данные и желаемый результат

4. Мне просто нужно было получить данные с максимальной датой, я думаю, что агрегатной функции нужно предложение group by.

Ответ №1:

Я уже понял это.

 select [data].Serial_Number,Time_Stamp,Inductive_Injection_Hours,Capacitive_Injection_Hours,b.Serial_Number from Converter_Tel_Data as [data]
inner join dbo.Converter AS c On [data].Converter_ID = c.Converter_ID
inner join dbo.Bypass as b on c.Bypass_ID = b.Bypass_ID
WHERE
  (Time_Stamp = (SELECT MAX(Time_Stamp) FROM Converter_Tel_Data WHERE Converter_ID = [data].Converter_ID)) And ([data].Site_ID=7)

 ORDER BY [data].Serial_Number
 

Комментарии:

1. Выбор первой (или последней, или 10 лучших или …) строк в группе-это постоянный вопрос. Хотя этого может быть достаточно в зависимости от вашего дизайна и использования, это не является надежным, поскольку предполагается, что все строки в группе имеют уникальное значение для метки времени (т. Е. Без дубликатов). Найдите альтернативы «первый в группе».

2. @SMor ты прав. у меня есть данные, в которых каждая временная метка строки уникальна. каково решение, если оно не уникально?

Ответ №2:

Вы можете использовать row_number — либо в таблице CTE/производной, либо с помощью трюка с ВЕРХНИМ 1.

 Select Top 1 With Ties
       bp.Serial_Number
     , tcon.Serial_Number AS ConverterSerialNumber
     , tcon.Time_Stamp AS DateStamp
     , tcon.Inductive_Injection_Hours
     , tcon.Capacitive_Injection_Hours
  From dbo.Bypass AS bp 
 Inner Join dbo.Converter AS c On bp.Bypass_ID = c.Bypass_ID 
 Inner Join dbo.Converter_Tel_Data AS tcon ON c.Converter_ID = tcon.Converter_ID
 Where bp.Site_ID = 7
 Order By
       row_number() over(Partition By bp.Serial_Number Order By tcon.Time_Stamp desc)
 

Это должно возвращать последнюю строку из таблицы tconn для каждого bp.Serial_Number.

Комментарии:

1. это не дает мне правильного вывода. этот запрос также занимает вдвое больше времени.