Listes ou tableaux en python

24 Apr 2019 24 Apr 2019 26808 vues ESSADDOUKI Mostafa 14 min de lecture

Les listes

Dans la plupart des problèmes informatiques, nous devons manipuler plusieurs valeurs : les notes des étudiants, les températures d'une semaine, une séquence de mesures expérimentales, les positions d'objets dans un algorithme de simulation, les résultats d'un sondage, etc.

Stocker ces valeurs dans des variables séparées n'est ni pratique, ni efficace :

note1 = 12
note2 = 14
# ...

Impossible de parcourir facilement ces données, de les trier, de les modifier, de faire des statistiques, etc. Python propose alors une structure simple, flexible et très puissante : les listes (list).

Définition et syntaxe

Définition Une liste est une structure de données ordonnée et modifiable (mutable) qui sert de conteneur pour stocker plusieurs valeurs de tout type, organisées dans un ordre précis.

Les listes sont incontournables en algorithmique et utilisées partout : parcours, tableaux, files d'attente, piles, traitements séquentiels…

Syntaxe
L = [élément1, élément2, élément3, ...]

Exemple — Création de listes

vide  = []
vide2 = list()

notes   = [12, 14, 16, 9]
noms    = ["Ismail", "Ikram", "Mohammed"]
voyelles = ['a', 'e', 'i', 'o', 'u']
mixte   = [1, "Python", True, 3.14]   # types hétérogènes
Typage hétérogène Contrairement à de nombreux langages, une liste Python peut contenir des éléments de types différents dans la même liste (entiers, chaînes, booléens, flottants, voire d'autres listes).

Accès et modification

Dans une liste, chaque élément occupe une position précise, repérable par son indice.

Définition — Indice Un indice est une position numérique qui identifie la localisation précise d'un élément dans une liste.

Python propose deux systèmes d'indexation complémentaires :

Élément1020304050
Indice positif01234
Indice négatif-5-4-3-2-1
  • Indexation positive : à partir du début de la liste. Le premier élément est à l'index 0, le deuxième à 1, l'index maximal est len(L) - 1.
  • Indexation négative : à partir de la fin. -1 désigne le dernier élément, -2 l'avant-dernier, etc.

Accès en lecture

Accès en lecture simple

Syntaxe
val = L[i]   # i est un indice entier (positif ou négatif)

Exemple

L = [10, 20, 30, 40, 50]
x = L[2]    # 30
y = L[-1]   # 50
z = L[-3]   # 30

Accès en lecture par tranche (slicing)

Le slicing permet d'extraire une sous-liste, sans modifier la liste d'origine.

Syntaxe
sous_liste = L[debut:fin:pas]
  • debut : indice du premier élément inclus (par défaut 0).
  • fin : indice du premier élément exclu (par défaut len(L)).
  • pas : pas entre les éléments (par défaut 1).

Exemple

L = [10, 20, 30, 40, 50, 60]

R1 = L[1:4]    # [20, 30, 40]         — indices 1, 2, 3
R2 = L[:3]     # [10, 20, 30]         — du début jusqu'à 3 (exclu)
R3 = L[3:]     # [40, 50, 60]         — de 3 jusqu'à la fin
R4 = L[:]      # [10, 20, 30, 40, 50, 60]  — copie complète
R5 = L[::2]    # [10, 30, 50]         — éléments d'indice pair
R6 = L[::-1]   # [60, 50, 40, 30, 20, 10] — liste inversée
Astuce — Copie d'une liste L[:] crée une copie superficielle de la liste : les modifications sur la copie n'affectent pas la liste originale (pour les éléments simples). Pour les listes imbriquées, voir deepcopy.

Accès en écriture

Accès en écriture simple

Syntaxe
L[i] = valeur

Exemple

L = [1, 2, 3, 4]
L[1] = 10    # L devient [1, 10, 3, 4]

Accès en écriture par tranche

Le slicing en écriture permet de modifier plusieurs éléments d'un coup, et même de modifier la taille de la liste.

Syntaxe
L[debut:fin:pas] = iterable
Remarque L'élément à droite doit être un itérable (liste, tuple, …), pas une seule valeur.

Exemple — Remplacer une sous-liste

L = [10, 20, 30, 40, 50]
L[1:4] = [100, 200, 300]
# L devient [10, 100, 200, 300, 50]

Exemple — Remplacer par une liste de taille différente

L = [1, 2, 3, 4, 5]
L[1:4] = [20]
# L devient [1, 20, 5]

Exemple — Insérer sans supprimer

L = [1, 2, 3]
L[1:1] = [10, 20]
# L devient [1, 10, 20, 2, 3]

Exemple — Supprimer une tranche

L = [1, 2, 3, 4, 5]
L[1:4] = []
# L devient [1, 5]

Parcours d'une liste

Le parcours d'une liste est une opération fondamentale en algorithmique : il consiste à visiter chaque élément afin de l'afficher, le traiter ou réaliser un calcul (somme, recherche, etc.). Python propose plusieurs façons de parcourir une liste, adaptées selon le contexte.

Parcours direct avec la boucle for

On récupère directement les valeurs stockées dans la liste, une par une. C'est la méthode la plus simple et la plus pythonique.

Syntaxe
for element in liste:
    # traitement de element

Exemple

notes = [10, 5, 17, 18, 2]

for note in notes:
    print(note)
  • Avantage : lisible, simple, évite les erreurs d'index.
  • Inconvénient : on n'a pas directement accès à l'indice.

Parcours avec range()

Cette méthode utilise un indice pour accéder aux éléments. On l'utilise lorsque l'on a besoin de modifier la liste ou d'utiliser explicitement l'indice.

Syntaxe
for i in range(len(liste)):
    # traitement de liste[i]

Exemple

notes = [10, 5, 17, 18, 2]
for i in range(len(notes)):
    print(f"Indice {i} -> {notes[i]}")
  • Avantage : contrôle total sur les indices.
  • Inconvénient : un peu plus verbeux, risque d'erreur sur les indices.
Cas où cette méthode est indispensable
  • Modifier les valeurs de la liste en place.
  • Comparer un élément avec son voisin (notes[i] vs notes[i+1]).
  • Parcourir une partie seulement (par ex. de 1 à len-2).

Parcours avec enumerate()

Cette méthode combine les avantages des deux précédentes : accès à l'indice et à la valeur. Python renvoie automatiquement un couple (indice, valeur) à chaque itération.

Syntaxe
for indice, valeur in enumerate(liste):
    # traitement de indice et valeur

Exemple

notes = [10, 5, 17, 18, 2]
for indice, note in enumerate(notes):
    print(f"{indice}: {note}")
  • Avantage : très propre, évite les erreurs d'index.
  • Recommandé dans la majorité des cas où l'indice est nécessaire.
MéthodeAccès valeurAccès indiceCas d'usage
for x in LDirectNonLecture simple, affichage
for i in range(len(L))Via L[i]OuiModification, comparaison voisins
for i, x in enumerate(L)DirectOuiMéthode recommandée

Les principales méthodes des listes

Les listes possèdent de nombreuses méthodes intégrées. Une méthode est une fonction appliquée à une liste sous la forme :

Syntaxe
liste.methode(arguments)

Ajouter un élément

append(x) — Ajouter en fin de liste

L = [1, 2]
L.append(3)
# L = [1, 2, 3]

insert(i, x) — Insérer à l'indice i

L = [1, 2, 3]
L.insert(1, 5)
# L = [1, 5, 2, 3]

extend(L2) — Concaténer deux listes

L = [1, 5, 2, 3]
L.extend([4, 6])
# L = [1, 5, 2, 3, 4, 6]
Différence append vs extend L.append([4, 6]) ajoute la liste [4, 6] comme un seul élément (liste imbriquée), tandis que L.extend([4, 6]) ajoute chaque élément séparément.

Supprimer un élément

pop(i) — Supprimer et retourner l'élément d'indice i

Si i n'est pas précisé, supprime le dernier élément.

L = [1, 5, 2, 3, 4, 6]
x = L.pop()    # x = 6,  L = [1, 5, 2, 3, 4]
y = L.pop(1)   # y = 5,  L = [1, 2, 3, 4]

remove(x) — Supprimer la première occurrence de x

L = [1, 2, 5, 3, 5]
L.remove(5)
# L = [1, 2, 3, 5]   (seule la première occurrence est supprimée)

clear() — Vider entièrement la liste

L.clear()
# L = []

Rechercher / compter

Opérateur in — Vérifier si un élément existe

L = [1, 5, 2, 3, 4, 6]

5 in L       # True
10 in L      # False
2 not in L   # False

C'est la méthode la plus rapide et la plus lisible quand on veut juste savoir si un élément est présent.

index(valeur) — Trouver l'indice d'un élément

Retourne l'indice de la première occurrence. Lève ValueError si l'élément est absent.

L = [1, 5, 2, 3, 4, 6, 5]
L.index(5)    # 1
L.index(6)    # 5
# L.index(10) -> ValueError: 10 is not in list

Pour éviter l'erreur quand l'élément n'existe pas :

if 6 in L:
    print(L.index(6))   # 5

count(valeur) — Compter les occurrences

L = [1, 5, 2, 3, 4, 6, 5]
L.count(5)    # 2
L.count(2)    # 1
L.count(10)   # 0
MéthodeDescriptionRetourModifie la liste
append(x)Ajoute x en finNone
insert(i, x)Insère x à l'indice iNone
extend(L2)Concatène L2 à la listeNone
pop(i)Supprime et retourne l'élément à l'indice iélément supprimé
remove(x)Supprime la 1ʳᵉ occurrence de xNone
clear()Vide la listeNone
index(x)Indice de la 1ʳᵉ occurrence de xint
count(x)Nombre d'occurrences de xint

Fonctions utiles avec les listes

Les fonctions suivantes ne sont pas des méthodes — elles s'appliquent directement sur la liste :

  • len(L) : taille de la liste.
  • sum(L) : somme des éléments (numériques).
  • max(L), min(L) : maximum et minimum.
  • list(range(a, b, p)) : créer une liste de nombres.
  • sorted(L) : retourne une copie triée sans modifier L.

Exemple

notes = [10, 5, 17, 18, 2]
print(len(notes))    # 5
print(sum(notes))    # 52
print(max(notes))    # 18
print(min(notes))    # 2
print(sum(notes) / len(notes))  # 10.4  (moyenne)

Trier et inverser une liste

Python offre plusieurs outils pour réorganiser les éléments d'une liste. On distingue les méthodes qui modifient la liste en place et les fonctions qui renvoient une nouvelle liste.

Méthode sort()

Trie directement la liste, sans créer une nouvelle liste. Le tri est croissant par défaut.

Syntaxe
L.sort()                   # tri croissant
L.sort(reverse=True)       # tri décroissant
L.sort(key=fonction)       # tri avec clé personnalisée

Exemple — Tri avec une clé

L = ["Python", "C", "JavaScript", "Go"]
L.sort(key=len)
print(L)   # ['C', 'Go', 'Python', 'JavaScript']

Fonction sorted(L)

Renvoie une copie triée de la liste sans modifier L. Utile lorsque l'on veut garder la liste originale intacte.

Syntaxe
sorted(L)                  # tri croissant
sorted(L, reverse=True)    # tri décroissant
sorted(L, key=f)           # tri avec clé

L.sort()sorted(L)
Modifie la liste✅ En place❌ Crée une copie
RetourNoneNouvelle liste triée
Liste originaleModifiéeIntacte

Méthode reverse()

Inverse directement la liste en place. Ne trie pas, ne compare pas les éléments : il ne fait que renverser l'ordre.

Syntaxe
L.reverse()

Exemple

L = [1, 2, 3, 4]
L.reverse()
print(L)   # [4, 3, 2, 1]

# Alternative sans modifier la liste :
L_inv = L[::-1]

Les listes en compréhension

Dans la programmation classique, pour construire une liste à partir d'une autre, on utilise généralement une boucle :

L = []
for x in range(5):
    L.append(x**2)

Cette approche fonctionne, mais elle est plus longue à écrire, moins lisible, et source d'erreurs. Python propose une syntaxe plus concise, inspirée du langage mathématique des ensembles :

Notation mathématique

L = { f(x) pour x ∈ E si condition }

Définition — Liste en compréhension Une liste en compréhension est une écriture compacte qui permet de : générer une liste, transformer les éléments, filtrer certains éléments, faire tout cela en une seule ligne.
Syntaxe
[nouvel_element for element in sequence if condition]

Exemple — Filtrer les nombres pairs

# Sans compréhension
pairs = []
for x in range(10):
    if x % 2 == 0:
        pairs.append(x)

# Avec compréhension
pairs = [x for x in range(10) if x % 2 == 0]
# [0, 2, 4, 6, 8]

Exemple — Transformer et filtrer

# Carrés des nombres impairs
impairs_carres = [x**2 for x in range(10) if x % 2 == 1]
# [1, 9, 25, 49, 81]

Exemple — Table de multiplication (double boucle)

table = [i*j for i in range(1, 5) for j in range(1, 5)]

Exemple — Condition dans l'expression

parite = ["pair" if x % 2 == 0 else "impair" for x in range(6)]
# ['pair', 'impair', 'pair', 'impair', 'pair', 'impair']
Astuce Les listes en compréhension sont non seulement plus concises, mais aussi plus rapides que les boucles équivalentes car elles sont optimisées au niveau de l'interpréteur Python.

Les listes imbriquées

Définition Une liste imbriquée est une liste dont certains éléments sont eux-mêmes des listes. C'est une manière de représenter des données organisées en dimensions multiples.

Elles sont indispensables pour représenter :

  • une matrice numérique ;
  • un tableau de données à plusieurs colonnes ;
  • une grille pour un jeu (échecs, sudoku, labyrinthe…) ;
  • un ensemble structuré : notes, coordonnées, table de multiplication, etc.

Exemple — Représenter une matrice

La matrice suivante :

Matrice 3×3

| 1 2 3 |
| 4 5 6 |
| 7 8 9 |

se représente en Python ainsi :

matrice = [
    [1, 2, 3],
    [4, 5, 6],
    [7, 8, 9]
]

Accéder aux éléments

Accéder à une liste interne (une « ligne »)

matrice = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]

premiere_ligne = matrice[0]   # [1, 2, 3]
deuxieme_ligne = matrice[1]   # [4, 5, 6]

Accéder à un élément spécifique (une « cellule »)

Syntaxe
liste[i][j]   # i = ligne,  j = colonne
  • Le premier indice [i] sélectionne la liste interne (la ligne).
  • Le deuxième indice [j] sélectionne l'élément dans cette ligne (la colonne).
element_5 = matrice[1][1]   # 5  (ligne 1, colonne 1)
element_7 = matrice[2][0]   # 7  (ligne 2, colonne 0)
element_3 = matrice[0][2]   # 3  (ligne 0, colonne 2)

Modification des éléments

# Remplacer l'élément 6 par 13
matrice[1][2] = 13
# matrice = [[1, 2, 3], [4, 5, 13], [7, 8, 9]]

Taille d'une structure imbriquée

  • Nombre de lignes : len(matrice)
  • Nombre de colonnes (tableau régulier) : len(matrice[0])

Ajouter et supprimer des éléments

Exemple — Ajouter une nouvelle ligne

M = [[1, 2], [3, 4]]
M.append([5, 6])
# M = [[1, 2], [3, 4], [5, 6]]

Exemple — Ajouter un élément dans une ligne

matrice = [[1, 2], [3, 4]]
matrice[0].append(20)
# matrice = [[1, 2, 20], [3, 4]]

Exemple — Supprimer un élément

matrice = [[1, 2, 3], [4, 5, 6]]
del matrice[1][0]   # Supprime 4 (ligne 1, colonne 0)
# matrice = [[1, 2, 3], [5, 6]]

Copier une liste imbriquée

Piège — Copie superficielle Utiliser =, .copy() ou le slicing [:] ne crée qu'une copie superficielle : seule la liste extérieure est copiée, les listes intérieures restent les mêmes objets en mémoire. Modifier la copie modifiera aussi l'original !

Pour garantir une copie totalement indépendante, utiliser copy.deepcopy() :

import copy

original      = [[1, 2], [3, 4]]
copie_superficielle = original[:]          # Dangereux !
copie_profonde      = copy.deepcopy(original)  # Sûr

copie_profonde[0][0] = 20

print(original)       # [[1, 2], [3, 4]]  — intacte
print(copie_profonde) # [[20, 2], [3, 4]]

Parcourir les listes imbriquées

L'itération se fait avec des boucles for imbriquées : la boucle externe parcourt les lignes, la boucle interne parcourt les colonnes.

Exemple — Itération 2D

matrice = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]

for ligne in matrice:
    for element in ligne:
        print(element, end=" ")
    print()   # Retour à la ligne après chaque ligne
Sortie
1 2 3
4 5 6
7 8 9

Exemple — Calculer la somme totale

matrice = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
n, m = len(matrice), len(matrice[0])
somme = 0
for i in range(n):
    for j in range(m):
        somme += matrice[i][j]

print(f"La somme des éléments est {somme}")  # 45
Sortie
La somme des éléments est 45
Astuce — Version concise avec compréhension La somme de tous les éléments d'une matrice peut s'écrire en une ligne : somme = sum(matrice[i][j] for i in range(n) for j in range(m)) ou encore sum(sum(ligne) for ligne in matrice).

Listes imbriquées en compréhension

La syntaxe pour créer une matrice 2D en compréhension imbrique une boucle for dans une autre :

Syntaxe
[[expression for j in iterable_interne] for i in iterable_externe]

Exemple — Matrice remplie de zéros (n × m)

n, m = 3, 4   # 3 lignes, 4 colonnes
matrice_zeros = [
    [0 for j in range(m)]   # créer une ligne de m zéros
    for i in range(n)       # répéter n fois
]
# [[0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0]]

Exemple — Table de multiplication

T = [[i*j for j in range(1, 11)] for i in range(1, 11)]

# Afficher proprement
for ligne in T:
    print(ligne)

Discussion (0)

Soyez le premier à laisser un commentaire !

Laisser un commentaire

Votre commentaire sera visible après modération.