L’un des moyens les plus simples, mais aussi les plus efficaces, d’affiner tes compétences de codeur c’est de rendre ton code plus lisible. Rendre ton code lisible le rend plus interprétable, plus reproductible et plus facile à déboguer. Et la meilleure façon de rendre ton code plus lisible est d’appliquer certaines règles, ou normes, pour le rendre cohérent et propre. Dans cet article, on s’attaque au langage SQL de la Data Science.
Ceci étant dit, je vais partager avec toi 8 conseils pour écrire du code SQL de tout premier ordre :
1. Mise en majuscules des mots-clés et des fonctions
Je commence par un conseil simple que tu suis peut-être déjà, ce qui est très bien, mais tu serais surpris du nombre de personnes qui ne respectent pas ce conseil : lorsqu’il s’agit de mots-clés et de fonctions, assure-toi qu’ils sont en majuscules !
Même si cela peut sembler être du chipotage, ce genre d’astuces rendra ton code dix fois plus lisible.
Au lieu de :
select name, date_trunc(register_date, week) from customers
Écris :
SELECT name, DATE_TRUNC(register_date, WEEK) FROM customers
2. Indentation et alignement
Pour poursuivre sur la lancée de l’exemple précédent, l’astuce suivante porte sur l’indentation et l’alignement du code. En considérant les deux exemples suivants de code SQL : lequel est le plus lisible ?
SELECT name, height, age, salary, CASE WHEN age<18 THEN "child" ELSE "adult" END AS child_or_adult FROM People LEFT JOIN Income USING (name) WHERE height<=200 and age<=65
ou
SELECT name , height , age , salary , CASE WHEN age < 18 THEN "child" ELSE "adult" END AS child_or_adult FROM People LEFT JOIN Income USING (name) WHERE height <= 200 AND age <= 65
Il est évident que le second est beaucoup plus facile à lire et cela est entièrement dû à son style de programmation ! En particulier, remarque comment ce code SQL est indenté et aligné verticalement dans le deuxième exemple. Il est ainsi beaucoup plus facile pour quelqu’un qui n’a jamais vu ton code de s’y retrouver.
Même si tu n’es pas obligé de suivre ce style exact d’indentation et de formatage, il est important de l’appliquer et de développer un style cohérent dans tout ton code.
3. Appliquer un type de cas cohérent pour les schémas, les tables et les colonnes
En programmation, il existe plusieurs types de case, pour n’en citer que quelques-uns :
- camelCase
- PascalCase
- snake_case
Quelle que soit ta préférence, il est important de t’assurer que tu es cohérent dans ton code.
Au lieu de :
SELECT firstName , LastName , child_or_adult FROM customers
Écris :
SELECT first_name , last_name , child_or_adult FROM customers
4. Évite les SELECT *
Il s’agit d’un conseil important, non seulement pour le formatage mais aussi pour l’optimisation des requêtes.
Même si tu te retrouves à utiliser presque toutes les colonnes d’un tableau, il est bon d’écrire les colonnes dont tu auras besoin. Pourquoi ? Au fur et à mesure que la table évolue et que d’autres colonnes sont ajoutées ou modifiées, le fait de spécifier les noms des colonnes facilitera l’identification de bugs potentiels à l’avenir.
Au lieu de :
SELECT * FROM customers
Écris :
SELECT name , height , age , salary FROM customers
5. Modulariser le code SQL avec des Common Table Expressions
L’utilisation d’expressions de table communes (ou CTE pour Common Table Expressions) est extrêmement utile pour modulariser et décomposer ton code – pensez-y de la même manière que tu décomposerais un essai en plusieurs paragraphes.
Consulte cet article si tu veux en savoir plus sur les CTEs, mais à la base, les CTEs créent une table temporaire qui te permet de « demander une requête ».
Au lieu de :
SELECT name , salary FROM People WHERE name IN (SELECT DISTINCT name FROM population WHERE country = "Canada" AND city = "Toronto") AND salary >= (SELECT AVG(salary) FROM salaries WHERE gender = "Female")
Écris :
with toronto_ppl as ( SELECT DISTINCT name FROM population WHERE country = "Canada" AND city = "Toronto" ) , avg_female_salary as ( SELECT AVG(salary) as avg_salary FROM salaries WHERE gender = "Female" ) SELECT name , salary FROM People WHERE name IN(SELECT name FROM toronto_ppl) AND salary >= (SELECT avg_salary FROM avg_female_salary)
Il est maintenant facile de voir que la clause WHERE
filtre les noms de Toronto. Les CTE sont utiles non seulement parce que tu peux décomposer ton code SQL en blocs plus petits, mais aussi parce que tu peux attribuer un nom de variable à chaque CTE (c’est-à-dire toronto_ppl et avg_female_salary).
En parlant de noms de variables, cela m’amène au point suivant :
Noms descriptifs des variables
Lorsque tu crées des noms de variables, tu veux qu’ils décrivent ce qu’ils représentent. En considérant mon exemple précédent :
with toronto_ppl as ( SELECT DISTINCT name FROM population WHERE country = "Canada" AND city = "Toronto" ) , avg_female_salary as ( SELECT AVG(salary) as avg_salary FROM salaries WHERE gender = "Female" ) SELECT name , salary FROM People WHERE name IN(SELECT name FROM toronto_ppl) AND salary >= (SELECT avg_salary FROM avg_female_salary)
En lisant simplement les noms des variables, il est clair que le premier CTE récupère les personnes de Toronto et que le second CTE obtient le salaire moyen des femmes.
D’un autre côté, il s’agirait d’un exemple de mauvaise convention de nommage (que j’ai déjà vu) :
with table_one as ( SELECT DISTINCT name FROM population WHERE country = "Canada" AND city = "Toronto" ) , table_two as ( SELECT AVG(salary) as var_1 FROM salaries WHERE gender = "Female" ) SELECT name , salary FROM People WHERE name IN(SELECT name FROM table_one) AND salary >= (SELECT var_1 FROM table_two)
7. Simplifier le code SQL en utilisant des fonctions temporaires
Les fonctions temporaires sont un excellent moyen de
- Décomposer le code,
- d’écrire un code SQL plus propre
- et de réutiliser le code.
Si tu souhaites en savoir plus sur les fonctions temporaires, tu peux lire cet article.
Prenons l’exemple suivant :
SELECT name , CASE WHEN tenure < 1 THEN "analyst" WHEN tenure BETWEEN 1 and 3 THEN "associate" WHEN tenure BETWEEN 3 and 5 THEN "senior" WHEN tenure > 5 THEN "vp" ELSE "n/a" END AS seniority FROM employees
Au lieu de cela, tu peux utiliser une fonction temporaire pour capturer la clause CASE
.
CREATE TEMPORARY FUNCTION seniority(tenure INT64) AS ( CASE WHEN tenure < 1 THEN "analyst" WHEN tenure BETWEEN 1 and 3 THEN "associate" WHEN tenure BETWEEN 3 and 5 THEN "senior" WHEN tenure > 5 THEN "vp" ELSE "n/a" END ); SELECT name , seniority(tenure) as seniority FROM employees
Avec une fonction temporaire, la requête elle-même est beaucoup plus simple, plus lisible, et tu peux réutiliser la fonction d’ancienneté !
8. Commentaires significatifs
Voici la règle la plus importante pour écrire des commentaires : N’écris des commentaires que lorsque tu en as besoin.
En suivant les sept conseils précédents (utiliser des noms descriptifs, modulariser le code, écrire du code propre, etc.), tu ne devrais pas avoir besoin d’écrire beaucoup de commentaires.
Ceci étant dit, les commentaires sont utiles, voire nécessaires, lorsque le code lui-même ne peut pas expliquer ce que tu essaies d’accomplir.
Voici un exemple de mauvais commentaire :
# Obtenir les noms des personnes à Toronto, au Canada with table1 as ( SELECT DISTINCT name FROM population WHERE country = "Canada" AND city = "Toronto" ) # Obtenir le salaire moyen des femmes , table2 as ( SELECT AVG(salary) as var1 FROM salaries WHERE gender = "Female" )
Ce sont de mauvais commentaires car ils nous disent ce que nous savons déjà en lisant le code lui-même. N’oublie pas que les commentaires répondent généralement à la question « pourquoi » tu fais quelque chose plutôt qu’à la question « ce que » tu fais.
Merci de m’avoir lu !
Tu ne sais pas quoi lire ensuite ? J’ai choisi un autre article pour toi :
3 pratiques que j’aurai aimé connaître en tant que Data Scientist junior
Et puis un autre :