2013-10-02 6 views
0

Пожалуйста, помогите мне объяснить, почему добавление предложения GROUP BY изменяет результаты запроса. Все остальное, оставаясь неизменным, удаление предложения GROUP BY приведет к другому результату, чем добавление предложения GROUP BY.MySQL - GROUP BY меняет результаты

Мне кажется, что GROUP BY просто группирует результаты с помощью поля, а не меняет счет.

мне нужно организовать данные по table2.name, и получить количество для каждого

SELECT table2.name, COUNT(DISTINCT(op.id)) 
FROM op INNER JOIN table1 ON table1.EID = op.ID 
    INNER JOIN table3 ON table3.id = table1.jobid 
    INNER JOIN table2 ON table2.id = table3.CatID 
WHERE op.ActiveStartDate <= NOW() 
    AND op.ActiveEndDate >= NOW() 
GROUP BY table2.name 
ORDER BY COUNT(*) DESC; 
+0

Мы не можем предсказать, что вы видите, пожалуйста, разделите оба результата запроса – Kuzgun

+0

Странность - это запрос работает без GROUP BY (потому что MySql применяет неявный LIMIT 1 для всех скалярных полей, не включенных в предложение GROUP BY) –

+1

Все агрегированные функции (например, 'count') рассчитывается на основе записи для группы, если она определена. В противном случае они основывают свои вычисления на полном наборе результатов. –

ответ

0

COUNT представляет собой совокупность функций, которые, как и других агрегатных функций, таких MIN, MAX, SUM т.д. применяются для каждого элемента внутри группы.

MySql является немного более гибким, чем другие БД, в том смысле, что он позволяет использовать COUNT(*) без GROUP BY: это не разрешено, например. SQL Server или Oracle.

+0

Что было бы лучшим способом написать запрос? – Ken

+0

Я бы лично написал его так, как это более декларативно и согласуется с другими диалектами SQL. – davek

+0

Извините, какой путь? То, как я это делаю, приводит к неправильному результату. Если я использую COUNT (*), результат также неверен. Если я использую COUNT (*) без GROUP BY, результат также неверен. – Ken

0

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

  • COUNT (DISTINCT (op.id))
  • ГРУППА ПО table2.name
  • COUNT (*)

К сожалению, я не знаю достаточно о внутренней работе MySQL, чтобы узнать, почему это имеет точный эффект, но я знаю, как ее исправить.

Раствор суб ВЫБРАТЬ т.е.

SELECT * 
FROM (
    SELECT 
     table2.name, 
     COUNT(DISTINCT(op.id)), 
     COUNT(*) as c 
    FROM op 
     JOIN table1 ON table1.EID = op.ID 
     JOIN table3 ON table3.id = table1.jobid 
     JOIN table2 ON table2.id = table3.CatID 
    WHERE 
     op.ActiveStartDate <= NOW() 
     AND op.ActiveEndDate >= NOW() 
    GROUP BY 
     table2.name 
) AS t 
ORDER BY 
    t.c DESC 

Надеюсь, это не сделает запрос слишком медленно!