Ваша первая задача - создать подзапрос, который доставит ваш table1
в форме электронного письма, выбора. Это выглядит так (https://www.db-fiddle.com/f/mbXAqAo6Y4MPd3jH9vAY4Q/0)
SELECT email, selection1 AS selection FROM table1
UNION ALL
SELECT email, selection2 AS selection FROM table1
UNION ALL
SELECT email, selection3 AS selection FROM table1
Далее, сделайте то же самое для вашей таблицы2. (https://www.db-fiddle.com/f/mbXAqAo6Y4MPd3jH9vAY4Q/1)
SELECT race1 AS race from table2
UNION ALL
SELECT race2 AS race from table2
UNION ALL
SELECT race3 AS race from table2
UNION ALL
SELECT race4 AS race from table2;
Затем необходимо выяснить, сколько значений race
соответствует каждому значению selection
. Это берет агрегатную функцию. Схема вашего запроса:
SELECT email, COUNT(race) races_chosen
FROM selections
JOIN races ON selections.selection = races.race
GROUP BY email
Здесь с помощью операции JOIN вы создаете набор результатов, который показывает каждое электронное письмо вместе с выбором, который также появился в гонках. Затем вы их подсчитываете.
Фактический запрос должен использовать ваши подзапросы. Похоже на это. (https://www.db-fiddle.com/f/mbXAqAo6Y4MPd3jH9vAY4Q/2)
SELECT email, COUNT(race) races_chosen
FROM (
SELECT email, selection1 AS selection FROM table1
UNION ALL
SELECT email, selection2 AS selection FROM table1
UNION ALL
SELECT email, selection3 AS selection FROM table1
) selections
JOIN (
SELECT race1 AS race from table2
UNION ALL
SELECT race2 AS race from table2
UNION ALL
SELECT race3 AS race from table2
UNION ALL
SELECT race4 AS race from table2
) AS races ON selections.selection = races.race
GROUP BY email
Наконец, вы можете изменить строку SELECT на эту, чтобы получить свои очки. (https://www.db-fiddle.com/f/mbXAqAo6Y4MPd3jH9vAY4Q/3)
SELECT email, COUNT(race) races_chosen, COUNT(races)*50 points
Несколько вещей, которые вы должны рассмотреть.
Не создавайте еще одну таблицу, содержащую это данные результата. Вместо этого используйте запрос, чтобы сгенерировать его, когда вам это нужно. Это проще, потому что вам не нужно выяснять, что изменилось, чтобы обновить дополнительную таблицу; Вы просто генерируете результаты на лету. SQL предназначен для такого рода операций.
Подзапросы, которые я вам дал, позволили вам взять ваши денормализованные таблицы и нормализовать их. Без денормализации их запрос на генерацию ваших результатов был бы гораздо более сложным. Ваши таблицы денормализованы, потому что они содержат несколько фактов в каждой строке.
Вот что я имею в виду. Ваша таблица2 использует одну строку, чтобы показать четыре разных расы. Вместо этого у вас должен быть один ряд на гонку. Тогда гораздо проще добавить еще одну расу к столу с помощью INSERT или удалить ее с помощью DELETE. Это также облегчает запрос.
Ваш table1
денормализован, потому что это способ обеспечить соблюдение вашего правила о том, что каждый адрес электронной почты может выбрать до трех рас. Это терпимое решение по разработке программного обеспечения. Но, если вы хотите позволить им добавить четвертую гонку в будущем, исправить ваше приложение становится сложнее.