add BBD's tp5

master
Antoine PEREDERII 2 years ago
parent 159999e70f
commit 64ec447f55

@ -2,6 +2,5 @@
<project version="4"> <project version="4">
<component name="VcsDirectoryMappings"> <component name="VcsDirectoryMappings">
<mapping directory="" vcs="Git" /> <mapping directory="" vcs="Git" />
<mapping directory="$PROJECT_DIR$/SAE/SAE2.06-Travail_d_equipe" vcs="Git" />
</component> </component>
</project> </project>

@ -1,4 +1,4 @@
-- \! clear \! clear
-- -- -- ? 1 - Écrire une fonction qui pour un match donné calcule le nombre de rebonds -- -- -- ? 1 - Écrire une fonction qui pour un match donné calcule le nombre de rebonds
-- -- -- ? pris par les joueurs qui nont pas débuté la rencontre. Proposez deux versions, -- -- -- ? pris par les joueurs qui nont pas débuté la rencontre. Proposez deux versions,
-- -- -- ? une utilisant les fonctions dagrégation et une autre utilisant un curseur mais aucune fonction dagrégation. -- -- -- ? une utilisant les fonctions dagrégation et une autre utilisant un curseur mais aucune fonction dagrégation.
@ -230,180 +230,184 @@
-- END; -- END;
-- $$ LANGUAGE plpgsql; -- $$ LANGUAGE plpgsql;
-- -- ? 10 - Vérifier que léquipe des Spurs a été meilleure à domicile quà lextérieur pendant la saison 2021. -- ? 10 - Vérifier que léquipe des Spurs a été meilleure à domicile quà lextérieur pendant la saison 2021.
-- SELECT isBestAtHome(id, '2021') AS best_at_home SELECT isBestAtHome(id, '2021') AS best_at_home
-- FROM Team FROM Team
-- WHERE abbreviation = 'SAS'; WHERE abbreviation = 'SAS';
-- -- ? 11 - Ecrire une fonction bestAtHome qui retourne une table avec les équipes (ids, abbréviations, noms et villes) -- ? 11 - Ecrire une fonction bestAtHome qui retourne une table avec les équipes (ids, abbréviations, noms et villes)
-- -- ? qui ont gagné au moins autant de matchs à domicile quà lextérieur lors de la saison passée en paramètre. -- ? qui ont gagné au moins autant de matchs à domicile quà lextérieur lors de la saison passée en paramètre.
-- CREATE OR REPLACE FUNCTION BestAtHome(GameSeason Game.season%TYPE) CREATE OR REPLACE FUNCTION BestAtHome(GameSeason Game.season%TYPE)
-- RETURNS TABLE(id Team.id%TYPE, abbreviation Team.abbreviation%TYPE, nom Team.nickname%TYPE, ville Team.city%TYPE) AS $$ RETURNS TABLE(id Team.id%TYPE, abbreviation Team.abbreviation%TYPE, nom Team.nickname%TYPE, ville Team.city%TYPE) AS $$
-- BEGIN BEGIN
-- RETURN QUERY SELECT DISTINCT t.id, t.abbreviation, t.nickname, t.city RETURN QUERY SELECT DISTINCT t.id, t.abbreviation, t.nickname, t.city
-- FROM Team t FROM Team t
-- WHERE isBestAtHome(t.id, GameSeason) = 1; WHERE isBestAtHome(t.id, GameSeason) = 1;
-- END; END;
-- $$ LANGUAGE plpgsql; $$ LANGUAGE plpgsql;
-- -- ? 12 - Quelles équipes ont gagné au moins autant de matchs à domicile quà lextérieur en 2021?
-- SELECT BestAtHome(2021);
-- -- ? 13 - Ecrire une fonction qui retourne un booléen indiquant si une équipe donnée à gagner au moins autant de matchs à
-- -- ? domiciles quà lextérieur pendant au moins n saisons consécutives, où n est un paramètre de la fonction.
-- -- ? Cette fonction devra lever une exception personnalisée si n nest pas une valeur possible.
-- CREATE OR REPLACE FUNCTION isBestAtHomeDuring(nbSeason numeric) RETURNS numeric AS $$
-- DECLARE
-- home_wins integer;
-- away_wins integer;
-- BEGIN
-- SELECT COUNT(*) INTO home_wins
-- FROM GAME g, Team t
-- WHERE g.idHomeTeam = t.id AND isBestAtHome(t.id, g.season) = 1;
-- SELECT COUNT(*) INTO away_wins
-- FROM GAME g, Team t
-- WHERE g.idVisitorTeam = t.id AND isBestAtHome(t.id, g.season) = 0;
-- IF (home_wins >= away_wins) THEN
-- RETURN 1;
-- ELSE
-- RETURN 0;
-- END IF;
-- END;
-- $$ LANGUAGE plpgsql;
-- CREATE OR REPLACE FUNCTION isBestAtHomeDuring(nbSeason numeric) RETURNS numeric AS $$ -- ? 12 - Quelles équipes ont gagné au moins autant de matchs à domicile quà lextérieur en 2021?
-- DECLARE
-- home_wins integer;
-- away_wins integer;
-- BEGIN
-- SELECT COUNT(*) INTO home_wins
-- FROM GAME g, Team t
-- WHERE g.idHomeTeam = t.id AND isBestAtHome(t.id, g.season) = 1;
-- SELECT COUNT(*) INTO away_wins SELECT BestAtHome(2021);
-- FROM GAME g, Team t
-- WHERE g.idVisitorTeam = t.id AND isBestAtHome(t.id, g.season) = 0;
-- IF (home_wins >= away_wins) THEN -- ? 13 - Ecrire une fonction qui retourne un booléen indiquant si une équipe donnée à gagner au moins autant de matchs à
-- RETURN 1; -- ? domiciles quà lextérieur pendant au moins n saisons consécutives, où n est un paramètre de la fonction.
-- ELSE -- ? Cette fonction devra lever une exception personnalisée si n nest pas une valeur possible.
-- RETURN 0;
-- END IF;
-- END;
-- $$ LANGUAGE plpgsql;
CREATE OR REPLACE FUNCTION isBestAtHomeDuring(teamID Team.id%TYPE, n integer) RETURNS boolean AS $$ CREATE OR REPLACE FUNCTION isBestAtHomeDuring(teamID Team.id%TYPE, n integer) RETURNS integer AS $$
DECLARE DECLARE
home_wins integer; home_wins integer;
away_wins integer; away_wins integer;
consecutive_seasons integer[]; consecutive_seasons integer;
BEGIN BEGIN
-- Vérifier que n est une valeur valide (n doit être supérieur ou égal à 1) -- Vérifier que n est une valeur valide (n doit être supérieur ou égal à 1)
IF n < 1 THEN IF n < 1 THEN
RAISE EXCEPTION 'La valeur de n doit être d''au moins 1.'; RAISE EXCEPTION 'La valeur de n doit être d''au moins 1.';
END IF; END IF;
-- Initialiser le tableau des saisons avec des victoires à domicile
consecutive_seasons := ARRAY[]::integer[];
-- Compter le nombre de saisons -- Compter le nombre de saisons
SELECT COUNT(DISTINCT season) INTO consecutive_seasons SELECT COUNT(DISTINCT season) INTO consecutive_seasons
FROM Game FROM Game
WHERE idHomeTeam = teamID OR idVisitorTeam = teamID; WHERE idHomeTeam = teamID OR idVisitorTeam = teamID;
-- Itérer sur les saisons -- Vérifier si l'équipe a gagné au moins autant de matchs à domicile qu'à l'extérieur pour n saisons consécutives
FOR i IN 1..consecutive_seasons - n + 1 LOOP FOR i IN 1..consecutive_seasons - n + 1 LOOP
-- Vérifier si l'équipe a gagné au moins autant de matchs à domicile qu'à l'extérieur pendant n saisons consécutives SELECT COUNT(*) INTO home_wins
home_wins := ( FROM Game
SELECT COUNT(*) WHERE season BETWEEN i AND i + n - 1
FROM GAME g AND idHomeTeam = teamID
WHERE g.season >= i AND ptsHome > ptsAway;
AND g.season <= i + n - 1
AND g.idHomeTeam = teamID SELECT COUNT(*) INTO away_wins
AND g.ptsHome > g.ptsAway FROM Game
); WHERE season BETWEEN i AND i + n - 1
AND idVisitorTeam = teamID
away_wins := ( AND ptsAway > ptsHome;
SELECT COUNT(*)
FROM GAME g
WHERE g.season >= i
AND g.season <= i + n - 1
AND g.idVisitorTeam = teamID
AND g.ptsAway > g.ptsHome
);
-- Si l'équipe a gagné au moins autant de matchs à domicile qu'à l'extérieur pendant n saisons consécutives, retourner vrai
IF home_wins >= away_wins THEN IF home_wins >= away_wins THEN
RETURN true; RETURN 1;
END IF; END IF;
END LOOP; END LOOP;
-- Si l'équipe n'a pas gagné au moins autant de matchs à domicile qu'à l'extérieur pendant n saisons consécutives, retourner faux RETURN 0;
RETURN false;
END; END;
$$ LANGUAGE plpgsql; $$ LANGUAGE plpgsql;
SELECT isBestAtHomeDuring('1610612737', 2021); SELECT isBestAtHomeDuring('1610612737', 1) AS best_at_home_during_one_seasons;
-- -- ? 14 - Y a til des équipes qui ont gagné au moins autant de matchs à domicile quà lextérieur -- ? 14 - Y a til des équipes qui ont gagné au moins autant de matchs à domicile quà lextérieur
-- -- ? pendant 2 saisons consécutives ? Pendant 3 saisons consécutives ? -- ? pendant 2 saisons consécutives ? Pendant 3 saisons consécutives ?
SELECT isBestAtHomeDuring('1610612737', 2) AS best_at_home_during_two_seasons;
SELECT isBestAtHomeDuring('1610612737', 3) AS best_at_home_during_three_seasons;
-- -- ? 15 - Écrire une fonction qui calcule lid de léquipe ayant le meilleur pourcentage moyen de paniers
-- -- ? à 3 points dune saison donnée.
-- CREATE OR REPLACE FUNCTION idTeam3Points(GameSeason Game.season%TYPE) RETURNS numeric AS $$ -- ? 15 - Écrire une fonction qui calcule lid de léquipe ayant le meilleur pourcentage moyen de paniers
-- DECLARE -- ? à 3 points dune saison donnée.
-- idTeam Team.id%TYPE;
-- BEGIN
-- SELECT t.id INTO idTeam
-- FROM Team t, GameDetail gd, Game g
-- WHERE gd.idTeam = t.id AND gd.idGame = g.id AND g.season = GameSeason AND gd.threePointsPrctage >= ALL(SELECT threePointsPrctage
-- FROM GameDetail gd1
-- WHERE gd1.idTeam = t.id);
-- RETURN idTeam;
-- END;
-- $$ LANGUAGE plpgsql;
-- -- ? 16 - Utiliser cette fonction pour afficher la meilleure équipe (abbréviation, nom et ville) de la saison 2021 en pourcentage moyen de paniers à 3 points CREATE OR REPLACE FUNCTION idTeam3Points(GameSeason numeric) RETURNS character varying AS $$
DECLARE
bestTeamID character varying;
BEGIN
SELECT INTO bestTeamID gd.idTeam
FROM GameDetail gd, Game g
WHERE gd.idGame = g.id AND g.season = GameSeason
GROUP BY gd.idTeam
ORDER BY AVG(gd.threePointsPrctage) DESC
LIMIT 1;
RETURN bestTeamID;
END;
$$ LANGUAGE plpgsql;
-- SELECT t.id, t.abbreviation, t.nickname, t.city
-- FROM Team t
-- WHERE idTeam3Points('2021') = t.id;
-- -- ? 17 - Écrire une fonction qui calcule combien de paniers à trois points ont été marqué par un joueur donné, pendant une saison donnée. -- ? 16 - Utiliser cette fonction pour afficher la meilleure équipe (abbréviation, nom et ville) de la saison 2021 en pourcentage moyen de paniers à 3 points
SELECT abbreviation, nickname, city
FROM Team
WHERE id = idTeam3Points('2021');
-- ! charge infiniment
-- ? 17 - Écrire une fonction qui calcule combien de paniers à trois points ont été marqué par un joueur donné, pendant une saison donnée.
-- CREATE OR REPLACE FUNCTION idTeam3Points(idPlayer Player.id%TYPE , GameSeason Game.season%TYPE) RETURNS numeric AS $$
-- DECLARE
-- idTeam Team.id%TYPE;
-- BEGIN
-- SELECT t.id INTO idTeam
-- FROM Team t, GameDetail gd, Game g, Player p
-- WHERE gd.idTeam = t.id AND gd.idGame = g.id AND p.id = idPlayer AND g.season = GameSeason AND gd.threePointsPrctage >= ALL(SELECT threePointsPrctage
-- FROM GameDetail gd1
-- WHERE gd1.idTeam = t.id);
-- RETURN idTeam;
-- END;
-- $$ LANGUAGE plpgsql;
-- -- ? 18 - Écrire une fonction qui calcule lid du joueur ayant marqué le plus de paniers à trois points pendant une saison donnée. CREATE OR REPLACE FUNCTION count3pointsbyplayer(idP character varying, GameSeason numeric) RETURNS numeric AS $$
DECLARE
totalThreePoints numeric;
BEGIN
SELECT SUM(gd.threePointsMade)
INTO totalThreePoints
FROM GameDetail gd
JOIN Game g ON gd.idGame = g.id
WHERE gd.idPlayer = idP AND g.season = GameSeason;
RETURN totalThreePoints;
END;
$$ LANGUAGE plpgsql;
SELECT count3pointsbyplayer('203932', '2021');
-- ? 18 - Écrire une fonction qui calcule lid du joueur ayant marqué le plus de paniers à trois points pendant une saison donnée.
CREATE OR REPLACE FUNCTION idPlayerMost3Points(GameSeason Game.season%TYPE) RETURNS Player.id%TYPE AS $$
DECLARE
best_player_id Player.id%TYPE;
BEGIN
SELECT gd.idPlayer INTO best_player_id
FROM GameDetail gd
JOIN Game g ON gd.idGame = g.id
WHERE g.season = GameSeason
GROUP BY gd.idPlayer
ORDER BY SUM(gd.threePointsMade) DESC
LIMIT 1;
RETURN best_player_id;
END;
$$ LANGUAGE plpgsql;
SELECT idPlayerMost3Points('2021');
-- ? 19 - En utilisant les fonctions précédement créées, écrire un bloc anonyme qui affiche pour chaque saison, par ordre chronologique,
-- ? le nom du joueur ayant marqué le plus de paniers à trois points ainsi que le nombres de paniers à trois points marqués.
DO $$
DECLARE
season_value Game.season%TYPE;
player_id Player.id%TYPE;
total_3_points numeric;
BEGIN
FOR season_value IN (SELECT DISTINCT season FROM Game ORDER BY season) LOOP
player_id := idPlayerMost3Points(season_value);
total_3_points := count3PointsByPlayer(player_id, season_value);
RAISE NOTICE 'Saison %: Joueur ID %, Nombre de paniers à trois points : %', season_value, player_id, total_3_points;
END LOOP;
END;
$$;
-- ? 20 - Ce calcul est très long. Pour effectuer un calcul plus efficace, nous allons créer une table supplémentaire permettant de stocker des statistiques.
-- ? Créer la table Stats(season, player, threePoints) contenant le nombre de paniers à trois points marqués par chaque joueur pendant une saison et
-- ? la remplir avec les données contenues dans GameDetail.
-- ? △! Penser à éliminer les valeurs NULL.
-- -- ? 19 - En utilisant les fonctions précédement créées, écrire un bloc anonyme qui affiche pour chaque saison, par ordre chronologique, CREATE TABLE Stats (
-- -- ? le nom du joueur ayant marqué le plus de paniers à trois points ainsi que le nombres de paniers à trois points marqués. season numeric,
player varchar(10),
threePoints numeric
);
-- -- ? 20 - Ce calcul est très long. Pour effectuer un calcul plus efficace, nous allons créer une table supplémentaire permettant de stocker des statistiques. -- Insertion des données de GameDetail dans la table Stats
-- -- ? Créer la table Stats(season, player, threePoints) contenant le nombre de paniers à trois points marqués par chaque joueur pendant une saison et INSERT INTO Stats (season, player, threePoints)
-- -- ? la remplir avec les données contenues dans GameDetail. SELECT g.season, gd.idPlayer, SUM(gd.threePointsMade)
-- -- ? △! Penser à éliminer les valeurs NULL. FROM GameDetail gd, Game g
WHERE gd.idGame = g.id AND gd.threePointsMade IS NOT NULL
GROUP BY g.season, gd.idPlayer;

Loading…
Cancel
Save