Как мне написать этот проклятый SQL-запрос? - PullRequest
3 голосов
/ 11 ноября 2011

Я - относительное уведомление sql, хочу учиться, но мне нужна помощь в составлении запроса.Если кто-нибудь может направить меня в правильном направлении, я был бы благодарен.

Стол - TeamRankings.Столбцы следующие:

score | qualities_id | team_id | year | source

Команды оцениваются по разным качествам для конкретных лет.Обратите внимание, что данной команде может быть назначено несколько баллов (каждая будет из другого источника).Аналогично, у данной команды может не быть вообще никаких очков за данный год.

Вот проблема:

Учитывая одно качество и список команд, я хочу найти списокгоды, за которые КАЖДАЯ из этих команд имеет хотя бы один результат.

Я пришел к этому из Rails (3.1), и я мог бы сделать это глупо, используя Active Record и несколько вызовов дБ.Но я хотел бы иметь возможность делать на чистом SQL.Бонусные баллы за помощь в Active Record, которая ограничивается одним вызовом дБ.

Большое спасибо

Ответы [ 3 ]

1 голос
/ 11 ноября 2011

Я не уверен, как вы передаете параметр через Ruby, но вот немного SQL.Вы можете присоединиться к таблице команд, чтобы получить название команды.Не входит в вашу схему, но ...

Select Distinct tr.Team_id, t.TeamName, tr.Year
From TeamRankings tr
  Inner Join Teams t
Where Exists (
  Select 1 From TeamRankings 
  Where Team_id=tr.TeamID and Year=tr.Year and qualityID=@qualityid
  )
1 голос
/ 11 ноября 2011

Используя только SQL, вам нужно сгруппировать данные по yar, а затем использовать предложение HAVING, чтобы проверить, присутствует ли каждая команда ...

SELECT
  year
FROM
  TeamRankings
WHERE
  team_id IN (<your_list>)
  AND qualities_id = <your quality id>
GROUP BY
  year
HAVING
  COUNT(DISTINCT team_id) = <your number of teams>

Интересный момент - как передать список в SQL-запрос.Моя обычная привычка - передавать строку идентификатора через запятую с идентификатором ', а затем использовать функцию sql, разбивающую эту строку на набор записей.Это, конечно, не выглядит элегантно, но я встречал гораздо больше, ммм, новых решений ...

SELECT
  year
FROM
  TeamRankings
INNER JOIN
  dbo.my_split_function(@list_of_ids) AS Team
    ON Team.id = TeamRankings.team_id
WHERE
  qualities_id = @quality_id
GROUP BY
  year
HAVING
  COUNT(DISTINCT team_id) = (SELECT COUNT(DISTINCT id) FROM dbo.my_split_function(@list_of_ids))
1 голос
/ 11 ноября 2011

Вот пример для случая, когда у вас будет 6 команд.Значение, которое вы тестируете в предложении HAVING (в моем примере - 6), должно соответствовать числу team_ids, включенных в предложение IN.

SELECT year
    FROM TeamRankings
    WHERE qualities_id = 1
        AND team_id IN (4,8,15,16,23,42)
    GROUP BY year
    HAVING COUNT(DISTINCT team_id) = 6;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...