coldwa.st
Tous les guidesProgrammationWebDonnéesOutilsBases de donnéesHaskellConceptsCabal & buildsChaîne d’outilsCompilateurPerformanceÉditeur & HLS

Haskell · syntaxe · listes

Les compréhensions de listes en Haskell, expliquées

Par ColdwastMis à jour le 14 juin 20266 min de lecture#haskell#lists#syntax
Du code source dans un éditeur en terminal
Les compréhensions de listes construisent une nouvelle liste à partir de listes existantes, en une seule expression lisible.

L’une des premières choses qui rendent Haskell élégant est la compréhension de liste : une façon concise de construire une nouvelle liste à partir de listes existantes, reflétant la notation mathématique en compréhension que vous vous rappelez peut-être de l’école. Ce guide explique la syntaxe, les générateurs multiples, les gardes, et le lien entre les compréhensions et map et filter.

La syntaxe de base

Une compréhension de liste a la forme [ output | generator, condition ]. Lisez la barre comme « tel que » :

-- the squares of 1 to 10
squares = [x*x | x <- [1..10]]
-- [1,4,9,16,25,36,49,64,81,100]

Ici x <- [1..10] est un générateur : il tire chaque x de la liste [1..10], et la partie avant la barre, x*x, est l’expression de sortie appliquée à chaque élément.

Ajouter des gardes (filtrage)

Lignes de code source sur un écran sombre
Lignes de code à l’écran — une garde ne conserve que les éléments qui satisfont une condition.

Une garde est une condition booléenne qui ne conserve que les éléments qui la satisfont :

-- even numbers from 1 to 20, doubled
result = [x*2 | x <- [1..20], even x]
-- [4,8,12,16,20,24,28,32,36,40]

Vous pouvez combiner plusieurs gardes, séparées par des virgules ; toutes doivent être vraies pour qu’un élément soit inclus.

Générateurs multiples

Avec plus d’un générateur, la compréhension itère sur chaque combinaison (comme des boucles imbriquées), dans l’ordre :

-- all pairs from two small lists
pairs = [(x, y) | x <- [1,2,3], y <- ['a','b']]
-- [(1,'a'),(1,'b'),(2,'a'),(2,'b'),(3,'a'),(3,'b')]

Le générateur le plus à droite varie le plus vite. Vous pouvez aussi faire dépendre un générateur ultérieur d’un précédent — par exemple en tirant y de [x..10].

Leur lien avec map et filter

Une compréhension est essentiellement map et filter sous une forme lisible unique. Ceux-ci sont équivalents :

[x*2 | x <- xs, even x]
map (*2) (filter even xs)

Utilisez ce qui se lit le mieux selon le cas. Les compréhensions brillent quand vous avez plusieurs générateurs ou plusieurs gardes ; map/filter se composent bien dans des pipelines point-free. Parce que Haskell est paresseux, une compréhension sur une liste infinie comme [1..] ne calcule que les éléments que vous consommez réellement.

FAQ

Qu’est-ce qu’un générateur dans une compréhension de liste ? La partie x <- xs : elle tire chaque valeur de x de la liste xs pour alimenter l’expression de sortie.

Qu’est-ce qu’une garde ? Une condition booléenne (comme even x) placée après une virgule ; seuls les éléments pour lesquels elle est vraie sont conservés.

Puis-je utiliser plusieurs générateurs ? Oui — la compréhension produit chaque combinaison, le générateur le plus à droite variant le plus vite, comme des boucles imbriquées.

Les compréhensions sont-elles juste map et filter ? Conceptuellement oui pour les cas simples ; les compréhensions sont souvent plus lisibles avec plusieurs générateurs ou gardes, tandis que map/filter se composent bien dans des pipelines.

Pour le langage derrière la syntaxe, voyez ce qu’est Haskell ; les compréhensions sont l’une des fonctionnalités qui le rendent concis et expressif.

Guide indépendant, maintenu par la communauté. coldwa.st est un site de ressources de programmation ; cet article est un écrit explicatif neuf et original sur les compréhensions de listes en Haskell, sans affiliation avec les mainteneurs du langage. Le code reflète le comportement standard de Haskell/GHC — vérifiez auprès de la documentation GHC actuelle.