Получить LIMIT 3 из выбора - PullRequest
       6

Получить LIMIT 3 из выбора

0 голосов
/ 17 декабря 2011

, пожалуйста, помогите мне с подзапросом. У меня есть 2 таблицы:

  1. посещения: id_viz, Data_viz, Medic_id
  2. медики: id_med, Nume, Prenume, Specialty

где посещения.Medic_id = medics.id_med,

и мне нужно найти первых 3 медиков как количество посещений для каждой специальности в 2005 году.

То, что мне удалось получить, это количество посещений / каждой специальности / каждого медика, но я не знаю, как найти первые 3 из каждой специальности: (.

Вот что я сделал до сих пор:

SELECT
  CONCAT(m.Nume,' ',m.Prenume) AS Medic,
  m.Specialty,
  COUNT(v.Data_viz) AS nrviz
FROM
  visits v
INNER JOIN
  medics m
ON(v.Medic_id=m.id_med)
WHERE
  YEAR(v.Data_viz) = 2005
GROUP BY
  Medic
ORDER BY
  m.Specialty,
  nrviz DESC

Я пытался использовать LIMIT 3, но, конечно, он не работает. Я думаю, что необходимо использовать подзапрос, но я не знаю как. Пожалуйста, помогите мне.

Ответы [ 2 ]

1 голос
/ 17 декабря 2011

В других СУБД (таких как PostgreSQL, Oracle или SQL Server) вы можете элегантно решить эту проблему с помощью оконной функции , как определено в стандарте SQL.Но MySQL не предоставляет эту функцию.

Пример для PostgreSQL :

SELECT specialty, medic, nrviz
FROM (
    SELECT m.specialty
          ,array_to_string(ARRAY[m.nume,m.prenume], ' ') AS medic
          ,count(v.data_viz) AS nrviz
          ,row_number() OVER (PARTITON BY m.specialty
                              ORDER BY count(v.data_viz) DESC) AS rn
    FROM   visits v
    JOIN   medics m ON (v.medic_id = m.id_med)
    WHERE  year(v.data_viz) = 2005
    GROUP  BY m.specialty, m.nume, m.prenume
    ) x
WHERE  rn <= 3
ORDER  BY specialty, nrviz DESC, medic;

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

Редактировать:

Топ 3 медика для каждой специальности может выглядеть следующим образом для MySQL (не проверено):

SELECT x.*
FROM  (SELECT @lim := 3, @spc := '') vars,
    (
    SELECT m.specialty
          ,concat(m.nume,' ',m.prenume) AS medic
          ,count(v.data_viz) AS nrviz
    FROM   visits v
    JOIN   medics m ON (v.medic_id = m.id_med)
    WHERE  year(v.data_viz) = 2005
    GROUP  BY 1, 2
    ORDER  BY 1, 3 DESC
    ) x
WHERE  CASE WHEN @spc <> x.specialty
            THEN @r := @lim
            ELSE @r := @r - 1
       END > 0
AND    (@spc := x.specialty) IS NOT NULL
ORDER  BY x.specialty, x.nrviz DESC, x.medic

Переменная для specialty (@spc) инициализируется пустой строкой - предполагается, что никогда не содержит пустую строку .Иначе инициализируйте к другому невозможному значению.Также предполагается, что specialty равняется NOT NULL .

. Он просматривает упорядоченные результаты запроса и отсчитывает от @lim (3), поэтому он принимает только первые три медика.по специальности (с наибольшим количеством посещений).Всякий раз, когда изменяется специализация, счетчик сбрасывается на @lim.

Таким образом MySQL пробирается в процедурных элементах с переменными сеанса в SQL на основе множеств.Я называю эту черную магию, но она должна выполнить работу.

0 голосов
/ 17 декабря 2011

Вот как будет выглядеть ваш запрос с подзапросом:

SELECT
CONCAT(m.Nume,' ',m.Prenume) AS Medic,
  m.Specialty,
COUNT(v.Data_viz) AS nrviz
FROM
  visits v
INNER JOIN
  medics m
ON(v.Medic_id=m.id_med)
WHERE
YEAR(v.Data_viz) = (SELECT...)
GROUP BY
  Medic
ORDER BY
  m.Specialitate,
  nrviz DESC

Что нужно знать о подзапросах, так это то, что они выполняются перед вашим основным запросом,

Надеюсь, это поможет!

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