15th Mar 2023 19 minutes de lecture 6 exemples utiles d'ETC dans SQL Server Tihomir Babic sql cte Table des matières Syntaxe des CTE dans SQL Server 6 exemples d'ETC dans SQL Server 1 : Trouver les nombres moyens les plus élevés et les plus bas des flux quotidiens 2 : Calculer le montant total moyen des droits payés par chanson 3 : Trouver l'album le plus diffusé de chaque artiste 4 : Calculer le nombre moyen de streams par chanson et le comparer au nombre moyen de streams par date 5 : Calculer la rémunération moyenne la plus élevée et la plus basse pour un album, par artiste 6 : Trouver le chemin le plus long entre Rotterdam et Amsterdam Quand utiliser les CTE ? Les ETC sont la porte d'entrée vers l'utilisation de SQL avancé! Comment pouvez-vous utiliser les CTE dans SQL Server dans votre vie professionnelle de tous les jours en tant que professionnel des données ? Nous allons répondre à cette question en vous donnant six exemples. CTE est l'abréviation de Common Table Expression. Il s'agit d'une fonctionnalité relativement nouvelle de SQL Server qui a été mise à disposition avec SQL Server 2005. Un CTE est un résultat temporaire nommé. Ce résultat n'est disponible que pour la requête qui l'exécute. Il n'est pas stocké et n'occupe donc pas d'espace disque. Un CTE est quelque peu similaire à une table temporaire et peut être utilisé comme n'importe quelle autre table. Les CTE sont le plus souvent utilisés avec une déclaration SELECT, mais ils peuvent également être utilisés avec INSERT, UPDATE et DELETE. Les CTE sont l'un des concepts les plus complexes de SQL Server. Pour profiter de leurs avantages, votre approche de l'apprentissage doit être soigneusement structurée et non précipitée. Notre cours Requêtes récursives in MS SQL Server vous montrera comment écrire un CTE simple dans SQL Server pour commencer. Vous apprendrez ensuite à écrire plusieurs CTE, à les imbriquer et à les utiliser dans les instructions SELECT, INSERT, UPDATE et DELETE. Enfin, vous apprendrez à connaître les structures de données hiérarchiques et graphiques et à utiliser les CTE récursifs dans SQL Server pour interroger ces données. Pour vous permettre de vous entraîner, le cours comporte 112 exercices interactifs à réaliser. Il existe, bien sûr, d'autres façons d'apprendre les CTE que vous pouvez également consulter. Syntaxe des CTE dans SQL Server En règle générale, la syntaxe des CTE dans SQL Server ressemble à l'exemple suivant : WITH cte AS ( SELECT ... ) SELECT ... FROM cte; Les CTE doivent toujours commencer par le mot-clé WITH. Viennent ensuite le nom de l'ETC, le mot-clé AS et les parenthèses. Vous définissez l'ETC entre ces parenthèses. La définition, comme vous le verrez dans nos exemples, implique l'écriture de l'instruction SELECT. Vous trouverez plus de détails dans cet article qui explique ce qu'est un ETC. 6 exemples d'ETC dans SQL Server 1 : Trouver les nombres moyens les plus élevés et les plus bas des flux quotidiens Dans les cinq premiers exemples, nous utiliserons le même ensemble de données. Il s'agit de données inventées provenant d'une plateforme de streaming musical imaginaire, que nous appellerons Terpsichore. L'ensemble de données se compose de trois tableaux. La première est artistet voici la requête de création de table. Cette table contient les colonnes suivantes : id - L'ID de l'artiste et la clé primaire de la table. artist_name - Le nom de l'artiste. idartist_name 1Prince 2Jimi Hendrix 3Santana Ce tableau présente trois artistes. La table suivante est albums. Voici la requête pour la créer. Et voici les colonnes qu'elle contient : id - L'ID de l'album et la clé primaire de la table. artist_id - L'artiste (et la clé étrangère de la table). album_title - Le titre de l'album. year_released - L'année de sortie de l'album. idartist_idalbum_titleyear_released 12Are You Experienced1967 22Axis: Bold as Love1967 31Dirty Mind1980 42Electric Ladyland1968 53Abraxas1970 6119991982 73Santana III1971 83Santana1969 91Prince1979 101Controversy1981 La table contient dix albums. La dernière table est streams. Il présente les données de diffusion en continu pour les chansons individuelles. Vous pouvez créer le tableau à l'aide de cette requête. Et les colonnes : id - L'ID du flux et la clé primaire de la table. artist_id - L'ID de l'artiste et une clé étrangère. album_id - L'ID de l'album et une clé étrangère. song_title - Le nom de la chanson. date - La date du stream. number_of_streams - Le nombre de fois que la chanson a été jouée à une date donnée. pay_per_stream - Valeur (en dollars) que Terpsichore verse aux artistes pour chaque diffusion. idartist_idalbum_idsong_titledatenumber_of_streamspay_per_stream 119I Wanna Be Your Lover2023-01-015970.013 216Little Red Corvette2023-01-014970.013 316D.M.S.R.2023-01-012170.013 413Uptown2023-01-0197480.013 513Do It All Night2023-01-012080.013 Ce tableau comporte 45 lignes. Nous ne vous montrerons que les cinq premières, afin que vous puissiez vous faire une idée de la logique du tableau. Et maintenant, l'exemple ! Commençons par écrire un seul CTE dans SQL Server. Nous allons le faire pour calculer le nombre moyen le plus élevé et le plus bas de flux quotidiens. Voici le code ; nous l'expliquerons plus loin : WITH daily_streaming AS ( SELECT date, MIN(number_of_streams) AS minimum_streaming, MAX(number_of_streams) AS maximum_streaming FROM streams GROUP BY date ) SELECT AVG(minimum_streaming) AS average_minimum_daily_streaming, AVG(maximum_streaming) AS average_maximum__daily_streaming FROM daily_streaming; Un CTE est idéal pour décomposer la logique de n'importe quel calcul dans SQL Server. N'oubliez pas que plusieurs chansons sont diffusées en continu au cours d'une même journée. L'objectif de notre CTE est d'obtenir le nombre le plus bas et le plus élevé de streams chaque jour. Comme indiqué précédemment, un CTE dans SQL Server commence toujours par le mot-clé WITH, suivi du nom du CTE. Notre CTE s'appelle daily_streaming. Le mot-clé AS est suivi d'une déclaration SELECT entre parenthèses, c'est-à-dire la définition de l'ETC. Nous l'utilisons, ainsi que les fonctions d'agrégation MIN() et MAX(), pour calculer le nombre le plus élevé et le plus bas de flux par date. L'instruction SELECT suivante utilise les données de l'ETC, en y faisant référence dans la clause FROM. Comme nous l'avons dit, un CTE peut être utilisé comme n'importe quelle autre table. Dans cette déclaration SELECT, nous utilisons la fonction d'agrégation AVG() pour obtenir la moyenne des pics et des creux des flux quotidiens. Le résultat montre que le point le plus bas moyen est de 90 flux. La moyenne des flux quotidiens les plus élevés est de 8 367. average_minimum_daily_streamingaverage_maximum__daily_streaming 908,367 2 : Calculer le montant total moyen des droits payés par chanson Mettons maintenant en pratique ce que nous avons appris. Nous allons à nouveau écrire un seul ETC. Le problème à résoudre est de trouver le montant total moyen payé par Terpsichore pour chaque chanson. Voici la solution : WITH paid_per_song AS ( SELECT song_title, SUM(number_of_streams * pay_per_stream) AS total_pay FROM streams GROUP BY id, song_title, pay_per_stream ) SELECT song_title, AVG(total_pay) AS average_total_pay FROM paid_per_song GROUP BY song_title ORDER BY average_total_pay DESC; Nous utilisons le CTE du serveur SQL pour calculer le montant total payé par chanson en multipliant le nombre de streams par le montant payé par stream, puis en l'additionnant à l'aide de la fonction d'agrégation SUM(). Il n'y a pas de changement dans la syntaxe du CTE : d'abord WITH, puis le nom du CTE, et ensuite AS. Nous utilisons ensuite un SELECT qui invoque l'ETC pour calculer la rémunération moyenne par chanson. C'est simple : utilisez AVG(), faites référence à l'ETC dans FROM et groupez par titre de chanson. La requête renvoie le résultat suivant : song_titleaverage_total_pay Uptown47.4803330 I Wanna Be Your Lover36.8203330 Little Red Corvette33.8693330 The Wind Cries Mary23.6138660 Do It All Night12.4063330 If 6 Was 97.7824000 Samba Pa Ti7.5735000 All Along the Watchtower5.2032000 Bold as Love4.7424000 Burning of the Midnight Lamp3.7333330 D.M.S.R.3.1633330 Taboo2.4871000 Jingo2.1604000 Everything's Coming Our Way1.5466000 Incident at Neshabur0.9207000 Nous constatons que la chanson "Uptown" a rapporté 47,4803330 $ au total. Les deuxième et troisième chansons en termes de revenus sont "I Wanna Be Your Lover" et "Little Red Corvette". Si vous êtes un fan de cet artiste, vous n'avez pas besoin de SQL pour savoir qui a écrit ces trois chansons. 3 : Trouver l'album le plus diffusé de chaque artiste Dans cet exercice, vous devez trouver l'album le plus diffusé de chaque artiste. Produisez le nom de l'artiste, le titre de l'album et le nombre de streams par album. Il s'agit là encore d'une requête ne comportant qu'un seul CTE. Cependant, elle est un peu plus complexe que les deux précédentes - il y a quelques JOIN et une fonction de fenêtre. WITH album_streaming AS ( SELECT artist_id, album_id, SUM(number_of_streams) AS streams_by_album, RANK() OVER (PARTITION BY artist_id ORDER BY SUM(number_of_streams) DESC) AS streaming_rank FROM streams GROUP BY artist_id, album_id ) SELECT artist_name, album_title, streams_by_album FROM album_streaming alst JOIN albums al ON alst.album_id = al.id JOIN artist ar ON al.artist_id = ar.id WHERE streaming_rank = 1; Là encore, la syntaxe CTE de SQL Server est familière. Concentrons-nous donc sur ce que fait cet ETC. Nous l'utilisons pour classer les albums par artiste. Tout d'abord, nous sélectionnons les ID de l'artiste et de l'album. Ensuite, nous utilisons SUM() pour calculer le nombre de flux par album. Vient ensuite la partie cruciale : le classement des résultats à l'aide de la fonction de fenêtre RANK(). Une fois la fonction invoquée, nous voyons la clause OVER() - une clause obligatoire pour les fonctions SQL window. Nous partitionnons l'ensemble de données en fonction de l'identifiant de l'artiste et nous classons les données dans chaque partition en fonction du nombre de flux, par ordre décroissant. Qu'est-ce que cela signifie en pratique ? Cela signifie que la fonction window classera les albums d'un artiste, puis le classement sera repris lorsque la fonction atteindra l'artiste suivant, et ainsi de suite. L'album de l'artiste ayant reçu le plus grand nombre de streams sera classé en premier dans sa partition. Si vous n'exécutez que l'instruction SELECT dans l'ETC, vous obtiendrez le résultat suivant : artist_idalbum_idstreams_by_albumstreaming_rank 1313,8201 168,5462 198,4973 257,7221 273,6672 281,9643 3111,0691 325,8712 344,1893 Comme vous pouvez le voir, les albums du premier artiste sont classés du premier au troisième, en fonction du nombre de streams. Lorsque nous atteignons le deuxième artiste, le classement recommence. Il en va de même pour le troisième artiste. Voyons maintenant ce que fait la deuxième instruction SELECT. En fait, ce n'est pas très compliqué. Elle renvoie le nom de l'artiste et de l'album ainsi que le nombre de streams. Ce qui complique cette requête, c'est que nous devons joindre trois tables. La première jointure est l'ETC album_streaming. Ensuite, nous la joignons avec albums puis avec la table artist . Enfin, nous filtrons les données à l'aide de la clause WHERE, car nous ne nous intéressons qu'à l'album le plus diffusé. Vous obtiendrez ce résultat : artist_namealbum_titlestreams_by_album PrinceDirty Mind13,820 Jimi HendrixAre You Experienced11,069 SantanaAbraxas7,722 L'album de Prince le plus diffusé est "Dirty Mind", avec 13 820 diffusions. Pour Jimi Hendrix, l'album le plus diffusé est "Are You Experienced", et pour Santana, c'est "Abraxas". Cette solution utilise les fonctions de fenêtre, voici donc un rappel de leur fonctionnement pour le classement des données. 4 : Calculer le nombre moyen de streams par chanson et le comparer au nombre moyen de streams par date Les choses se compliquent maintenant. Mais pas trop, ne vous inquiétez pas. Nous nous appuyons sur ce que nous avons appris jusqu'à présent sur les CTE dans le serveur SQL. Ici, nous devons trouver le nombre moyen de flux par chanson. Nous devons ensuite calculer le nombre moyen de flux par date. La sortie doit indiquer les deux mesures. Elle doit également indiquer la différence entre le nombre moyen de streams par chanson et la moyenne quotidienne (en pourcentage), le titre de la chanson et les dates. Jusqu'à présent, nous avons écrit des requêtes avec un CTE. Cette fois, la solution consiste en deux CTE. Voyons comment cela fonctionne : WITH streams_per_song AS ( SELECT song_title, AVG(number_of_streams) AS average_streams_per_song FROM streams GROUP BY song_title ), streams_per_date AS ( SELECT date, AVG(number_of_streams) AS average_streams_per_date FROM streams GROUP BY date ) SELECT song_title, average_streams_per_song, date, average_streams_per_date, (average_streams_per_song - average_streams_per_date)/CAST(average_streams_per_date AS DECIMAL(10,2))*100 AS diff_from_daily_average FROM streams_per_song, streams_per_date; Le premier ETC est écrit comme d'habitude. Nous l'utilisons pour calculer le nombre moyen de streams par chanson avec AVG(). Après avoir fermé les parenthèses, la première ETC doit être séparée de la seconde par une virgule. Ensuite, nous écrivons la deuxième ETC. Et voilà ! Il n'y a pas de WITH! C'est exact. Lorsque vous écrivez plusieurs CTE dans une requête dans SQL Server, vous écrivez WITH uniquement devant le premier CTE. Le deuxième (et tout autre CTE suivant) commence par le nom du CTE ; tout le reste est identique. Cette deuxième requête permet de calculer le nombre moyen de flux par date. Là encore, nous utilisons la fonction AVG(). Le troisième site SELECT utilise les données des deux CTE. Elle renvoie toutes les colonnes requises. La dernière colonne est diff_from_daily_average. Nous la calculons en soustrayant le nombre moyen de streams par date du nombre moyen de streams par chanson. La différence est divisée par la moyenne des flux par date et multipliée par 100 pour obtenir le pourcentage. Nous avons également converti le résultat en un type de données décimal à l'aide de la fonction CAST(). En raison de la taille de la sortie, nous n'afficherons que les premières lignes : song_titleaverage_streams_per_songdateaverage_streams_per_datediff_from_daily_average All Along the Watchtower8132023-01-011,031-21.14 Bold as Love7412023-01-011,031-28.13 Burning of the Midnight Lamp5832023-01-011,031-43.45 D.M.S.R.2432023-01-011,031-76.43 Do It All Night9542023-01-011,031-7.47 Les données montrent que le flux quotidien moyen pour le 1er janvier 2023 est de 1 031. "All Along the Watchtower" est 21,14 % en dessous de cette moyenne. Les deux chansons suivantes sont 28,13 % et 43,45 % en dessous de la moyenne quotidienne, et ainsi de suite. 5 : Calculer la rémunération moyenne la plus élevée et la plus basse pour un album, par artiste Expliquons ce que nous entendons par là. Nous voulons d'abord trouver la rémunération moyenne par album et par date. Ensuite, nous devons trouver la rémunération la plus basse et la plus élevée par album. Ensuite, nous voulons agréger les données par artiste. En plus de son nom, nous devons afficher la valeur de la rémunération la plus basse que l'artiste a reçue pour un album. Nous devons faire de même avec la rémunération la plus élevée pour un album. La solution dans SQL Server contient deux CTE. Cependant, il s'agit cette fois d'un CTE imbriqué. En effet, le deuxième CTE fait référence au premier CTE. Voyons comment cela fonctionne : WITH pay_per_album AS ( SELECT album_id, date, AVG(number_of_streams * pay_per_stream) AS average_pay_per_album FROM streams GROUP BY album_id, date ), min_max_average_pay AS ( SELECT album_id, MIN(average_pay_per_album) AS lowest_average_pay_by_album, MAX(average_pay_per_album) AS highest_average_pay_by_album FROM pay_per_album GROUP BY album_id ) SELECT artist_name, MIN(lowest_average_pay_by_album) AS lowest_album_pay_by_artist, MAX(highest_average_pay_by_album) AS highest_album_pay_by_artist FROM min_max_average_pay mmap JOIN albums al ON mmap.album_id = al.id JOIN artist ar ON al.artist_id = ar.id GROUP BY artist_name; Faites attention lorsque vous lisez l'explication du code ! Il est facile de se perdre dans toutes ces agrégations. Pour faciliter les choses, j'ai copié chaque partie de la requête et l'ai fait suivre d'une explication. Nous allons commencer par le premier CTE : WITH pay_per_album AS ( SELECT album_id, date, AVG(number_of_streams * pay_per_stream) AS average_pay_per_album FROM streams GROUP BY album_id, date ), Le premier CTE calcule la rémunération moyenne par album et la date. Pour ce faire, on multiplie le nombre de streams par la rémunération par stream et on utilise AVG(). min_max_average_pay AS ( SELECT album_id, MIN(average_pay_per_album) AS lowest_average_pay_by_album, MAX(average_pay_per_album) AS highest_average_pay_by_album FROM pay_per_album GROUP BY album_id ) Lors de l'écriture du deuxième CTE dans SQL Server, la syntaxe est la même que dans l'exemple précédent - pas de WITH supplémentaire, commencez par le nom du CTE et séparez les CTE par une virgule. La seule différence est que, cette fois, le deuxième CTE fait référence au premier CTE, et non à l'ensemble de données d'origine. Cet ETC imbriqué utilise les fonctions MIN() et MAX() pour trouver la rémunération moyenne la plus basse et la plus élevée de chaque album pour toutes les dates. Le premier CTE est référencé dans la fonction FROM. SELECT artist_name, MIN(lowest_average_pay_by_album) AS lowest_album_pay_by_artist, MAX(highest_average_pay_by_album) AS highest_album_pay_by_artist FROM min_max_average_pay mmap JOIN albums al ON mmap.album_id = al.id JOIN artist ar ON al.artist_id = ar.id GROUP BY artist_name; Enfin, le site SELECT relie le deuxième CTE avec les fonctions albums et artist . Nous appliquons à nouveau les fonctions MIN() et MAX() au résultat du deuxième CTE. Il s'agit de renvoyer uniquement les valeurs de l'album le moins payé et de l'album le plus payé de tous les albums de chaque artiste. Voici ce que nous obtenons après avoir exécuté la requête : artist_namelowest_album_pay_by_artisthighest_album_pay_by_artist Jimi Hendrix1.5963.19 Prince4.6497.31 Santana0.9110.22 6 : Trouver le chemin le plus long entre Rotterdam et Amsterdam Il s'agit d'une variante du problème du plus court chemin dans la théorie des graphes, sauf que nous chercherons le chemin le plus long. Un graphe est un type de structure de données composé de nœuds ou de points reliés par des arêtes. Comme ils sont connectés, il est possible de trouver un chemin d'un nœud à l'autre, même s'ils ne sont pas directement connectés. Il s'agit d'une carte des routes. C'est exactement l'exemple que nous allons utiliser ici. Voici le tableau cities_distancequi montre les villes et la distance qui les sépare. Utilisez cette requête pour créer le tableau, qui contient les colonnes suivantes : city_from - La ville d'origine. city_to - La ville d'arrivée. distance - La distance entre les deux villes, en kilomètres. Voici les données : city_fromcity_todistance RotterdamAmsterdam78.20 RotterdamGouda24.10 AmsterdamGouda72.50 GoudaLeiden34.10 AmsterdamLeiden50.00 RotterdamLeiden35.40 GoudaUtrecht44.00 UtrechtAmsterdam52.40 LeidenGouda34.10 Nous devons trouver le chemin le plus long entre Rotterdam et Amsterdam. Le chemin doit inclure le nom de toutes les villes situées sur le trajet, séparées par des '/'. Nous devons également indiquer la longueur du chemin le plus long. Lorsque nous parlons du chemin le plus long, nous voulons exclure les chemins circulaires (où l'on peut faire des tours à l'infini et augmenter la distance). Nous voulons que ce chemin le plus long ne passe qu'une seule fois par une ville donnée. Pour résoudre ce problème, nous utiliserons un CTE récursif. Il s'agit d'une requête qui se réfère à elle-même jusqu'à ce qu'elle atteigne la fin des données. Cette caractéristique est idéale pour l'interrogation de données graphiques, où plusieurs chemins peuvent mener au même objectif. Voyons comment fonctionne cet ETC récursif : WITH longest_path AS ( SELECT cd.city_to, CAST((cd.city_from + '/' + cd.city_to) AS VARCHAR(100)) AS path, cd.distance AS distance FROM cities_distance cd WHERE cd.city_from = 'Rotterdam' UNION ALL SELECT cd.city_to, CAST((lp.path + '/' + cd.city_to) AS VARCHAR(100)) AS path, CAST((lp.distance + cd.distance) AS DECIMAL(10,2)) FROM longest_path lp INNER JOIN cities_distance cd ON cd.city_from = lp.city_to WHERE lp.city_to <> 'Amsterdam' AND lp.path NOT LIKE '%/' + cd.city_to + '/%' ) SELECT TOP 1 lp.path, lp.distance FROM longest_path lp WHERE lp.city_to = 'Amsterdam' ORDER BY lp.distance DESC; La syntaxe est la même que précédemment - la requête récursive commence également par WITH dans SQL Server. Comme d'habitude, il y a une déclaration SELECT entre parenthèses. Il y en a deux, pour être plus précis. Voyons ce que fait la première. WITH longest_path AS ( SELECT cd.city_to, CAST((cd.city_from + '/' + cd.city_to) AS VARCHAR(100)) AS path, cd.distance AS distance FROM cities_distance cd WHERE cd.city_from = 'Rotterdam' Le premier SELECT dans la récursion est appelé le membre d'ancrage. Il est utilisé pour sélectionner le point de départ de la récursion. Le point de départ sera Rotterdam, que nous obtenons en filtrant cette ville dans WHERE. La colonne city_to est utilisée pour afficher toutes les destinations finales qui peuvent être atteintes directement à partir de Rotterdam. La colonne path énumère toutes les villes d'origine et de destination. La longueur de cet itinéraire est indiquée dans la colonne distance. Vient ensuite UNION ALL, qui relie les résultats de l'ancre et du membre récursif, c'est-à-dire le second SELECT. L'union de ces deux requêtes est nécessaire pour que la récursivité fonctionne. Remarque : dans certains autres dialectes SQL, il est également possible d'utiliser UNION. Cependant, SQL Server n'autorise que UNION ALL. Nous en arrivons maintenant au membre récursif. Il fait référence à l'ETC lui-même dans FROM et le joint à la table cities_distance. Pour que les requêtes soient unifiées, elles doivent toutes deux avoir le même nombre de colonnes du même type de données. Les deux premières colonnes sont les mêmes que dans le membre d'ancrage. La colonne longest_path additionne toutes les distances parcourues pour atteindre toutes les villes à partir de Rotterdam. SELECT cd.city_to, CAST((lp.path + '/' + cd.city_to) AS VARCHAR(100)) AS path, CAST((lp.distance + cd.distance) AS DECIMAL(10,2)) FROM longest_path lp INNER JOIN cities_distance cd ON cd.city_from = lp.city_to WHERE lp.city_to <> 'Amsterdam' AND lp.path NOT LIKE '%/' + cd.city_to + '/%' ) Nous avons également ajouté deux conditions dans WHERE. La première exclut toutes les relations où Amsterdam est la destination finale ; nous recherchons le chemin le plus long, et non le plus court, vers Amsterdam. La deuxième condition garantit que toute nouvelle ville ajoutée au chemin n'est pas déjà incluse dans le chemin. Dans le cas contraire, la requête entrera dans une récursivité sans fin. Cela répond à ce que nous avons dit plus haut : le chemin le plus long ne doit pas visiter la même ville plus d'une fois. Pour mieux comprendre ce dont nous parlons, voici la sortie de l'ETC récursif : city_topathdistance AmsterdamRotterdam/Amsterdam78.20 GoudaRotterdam/Gouda24.10 LeidenRotterdam/Leiden35.40 GoudaRotterdam/Leiden/Gouda69.50 UtrechtRotterdam/Leiden/Gouda/Utrecht113.50 AmsterdamRotterdam/Leiden/Gouda/Utrecht/Amsterdam165.90 LeidenRotterdam/Gouda/Leiden58.2 UtrechtRotterdam/Gouda/Utrecht68.1 AmsterdamRotterdam/Gouda/Utrecht/Amsterdam120.5 Vous pouvez constater qu'il existe trois chemins entre Rotterdam et Amsterdam. L'un est direct, avec une distance de 78,20 km. Le deuxième et le troisième passent par d'autres villes et prennent respectivement 165,90 et 120,50 km. Attention, il ne s'agit pas du résultat final ! Notre solution comporte également une instruction SELECT qui fait référence à l'ETC : SELECT TOP 1 lp.path, lp.distance FROM longest_path lp WHERE lp.city_to = 'Amsterdam' ORDER BY lp.distance DESC; Ce site SELECT renvoie le chemin et la distance. Nous utilisons la commande TOP 1 combinée à ORDER BY pour obtenir le chemin le plus long entre Rotterdam et Amsterdam. Nous avons trié les données de la distance la plus élevée à la plus courte, de sorte que la première ligne correspondra également au chemin le plus long. Voici le résultat final : pathdistance Rotterdam/Leiden/Gouda/Utrecht/Amsterdam165.90 Ce résultat montre que le chemin le plus long de Rotterdam à Amsterdam est de 165,9 km et passe par Leiden, Gouda et Utrecht. Si vous ne vous lassez pas de ce sujet, voici d'autres exemples d'ETC. Quand utiliser les CTE ? Comme vous l'avez vu dans nos exemples, un CTE a de nombreuses fonctions dans SQL Server. L'un d'entre eux est qu'il améliore généralement la lisibilité du code. Toutes les solutions ci-dessus (à l'exception de la récursion) auraient pu être écrites avec des sous-requêtes. Mais le code serait alors beaucoup plus long et moins clair. À bien y réfléchir, les sous-requêtes sont généralement écrites à l'encontre de la logique du problème que vous essayez de résoudre. Vous avez d'abord la requête principale, qui utilise la sortie de la sous-requête. La sous-requête est donc généralement la première étape du calcul, même si elle n'est pas positionnée de cette manière dans le code. Les CTE, en revanche, peuvent être écrits de manière à suivre la logique du problème. Vous pouvez écrire plusieurs CTE distincts et fusionner leurs résultats dans les instructions SELECT. Vous pouvez également faire référence à la sortie d'un CTE avec la deuxième requête (ou la troisième, la quatrième...), l'instruction SELECT finale constituant un autre niveau de calcul. L'un des exemples montre également qu'il est possible de classer des données dans SQL Server à l'aide d'une fonction window et d'un CTE. Si vous souhaitez écrire des requêtes récursives dans SQL Server, vous ne pouvez pas le faire sans CTE. Un CTE peut être non récursif, mais aucune requête récursive n'existe sans CTE. Outre les graphes, la récursivité est extrêmement utile pour interroger les structures hiérarchiques, telles que l'organisation des données et les arbres généalogiques. Pour en savoir plus sur l'utilisation d'un ETC, cliquez ici. Les ETC sont la porte d'entrée vers l'utilisation de SQL avancé! Les CTE sont l'un des concepts les plus avancés de SQL Server. Si vous voulez accéder à des compétences SQL Server de niveau avancé, les CTE sont indispensables. Au fur et à mesure que vos requêtes dans SQL Server deviennent plus complexes, vous vous rendrez compte que l'apprentissage des CTE a été l'une des meilleures décisions que vous ayez jamais prises. Ils constituent également un tremplin vers les requêtes récursives, vous permettant d'interroger des types inhabituels de structures de données dans SQL Server, tels que les hiérarchies et les graphiques. Cet article n'est qu'un aperçu des connaissances que vous trouverez dans le cours Requêtes récursives in MS SQL Server. Ne vous arrêtez donc pas là. Il y a encore beaucoup à apprendre ! Tags: sql cte