Группировать по верному имени для максимального значения в другом поле - PullRequest
1 голос
/ 21 января 2020

Извините за вопрос с плохим названием, но у меня есть следующие данные примера:

Account ID     Name     Order Value
1122           John      2000
1122           Dave      1500

Для многих тысяч учетных записей (в моем примере обучения). То, что я пытаюсь сделать, это группировать по идентификаторам аккаунтов, чтобы получить максимальное значение заказа для каждого аккаунта, , но меня также интересует, кто сделал этот заказ для каждого идентификатора аккаунта .

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

SELECT Data.[Account ID], min(Data.Name), max(Data.[Order Value])

group by Data.[Account ID]

Однако это возвращает Дейва (из-за функции min ()) против значения Order 2000, где, как я хотел бы видеть Имя Джона Как я могу получить имя, связанное с максимальным значением заказа для каждой учетной записи?

Ответы [ 3 ]

0 голосов
/ 21 января 2020

Не думай "группировать по". Подумайте, «фильтр». Вы хотите получить полную строку с максимальным значением заказа.

Вот один из методов:

select t.*
from t
where t.order_value = (select max(t2.order_value)
                       from t as t2
                       where t2.account_id = t.account_id
                      );
0 голосов
/ 21 января 2020

Вы также можете использовать коррелированный подзапрос в предложении where not exists:

select d.* from data d
where not exists 
(
    select 1 from data t where
    t.[Account ID]  = d.[Account ID] and 
    t.[Order Value] > d.[Order Value]
)

Обратите внимание, что:

  • t & d являются псевдонимами, разрешающими Data, на который будет ссылаться дважды в одном запросе.
  • select 1 предназначен исключительно для оптимизации: нам не важно, что возвращает подзапрос, просто что у него есть записи (или, в данном случае, нет). записи).

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

select d.* from data d inner join
(
    select t.[Account ID], max(t.[Order Value]) as mov
    from data t
    group by t.[Account ID]
) q on
d.[Account ID]  = q.[Account ID] and 
d.[Order Value] = q.mov
0 голосов
/ 21 января 2020

Это типичный топ 1 для группового вопроса. Вы не можете решить это только с помощью агрегации.

В одном варианте используется анти- left join:

select d.*
from [Data] d
left join [Data] d1 
    on  (d1.[Account ID] = d.[Account ID])
    and (d1.[Order Value] > d.[Order Value])
where d1.[Account ID] is null

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

...