end - LIFL

Transcription

end - LIFL
Algorithmique et Programmation
Impérative 2
Enregistrements, Pointeurs,
Structures chaînées
N.E. Oussous
[email protected]
FIL – USTL
API2 - LST«A» – p.1/42
Introduction
➻ Structurer les données pour mieux les manipuler
API2 - LST«A» – p.2/42
Introduction
➻ Structurer les données pour mieux les manipuler
➻ Si les données sont homogènes (même type)
API2 - LST«A» – p.2/42
Introduction
➻ Structurer les données pour mieux les manipuler
➻ Si les données sont homogènes (même type)
➠ on peut utiliser un tableau
API2 - LST«A» – p.2/42
Introduction
➻ Structurer les données pour mieux les manipuler
➻ Si les données sont homogènes (même type)
➠ on peut utiliser un tableau
➻ Si les données sont hétérogènes (de types différents)
API2 - LST«A» – p.2/42
Introduction
➻ Structurer les données pour mieux les manipuler
➻ Si les données sont homogènes (même type)
➠ on peut utiliser un tableau
➻ Si les données sont hétérogènes (de types différents)
➠ on utilise une structure d’enregistrement
API2 - LST«A» – p.2/42
Exemple
Un employé d’une entreprise peut être défini par
➻ son nom (chaîne de caractères)
API2 - LST«A» – p.3/42
Exemple
Un employé d’une entreprise peut être défini par
➻ son nom (chaîne de caractères)
➻ son adresse (chaîne de caractères)
API2 - LST«A» – p.3/42
Exemple
Un employé d’une entreprise peut être défini par
➻ son nom (chaîne de caractères)
➻ son adresse (chaîne de caractères)
➻ son salaire (réel)
API2 - LST«A» – p.3/42
Exemple
NOM
ADRESSE
employé
Un employé d’une entreprise peut être défini par
➻ son nom (chaîne de caractères)
➻ son adresse (chaîne de caractères)
➻ son salaire (réel)
Notons
➻ NOM l’ensemble des noms
➻ ADRESSE l’ensemble des adresses
➻ SALAIRE l’ensemble des salaires
Alors
SALAIRE (un triplet)
API2 - LST«A» – p.3/42
Enregistrement
Enregistrement = structure = article = record
➻ Pour représenter les -uplets
API2 - LST«A» – p.4/42
Enregistrement
Enregistrement = structure = article = record
➻ Pour représenter les -uplets
➻ C’est un objet constitué de composants nommés
pouvant être de types différents
API2 - LST«A» – p.4/42
Enregistrement
Enregistrement = structure = article = record
➻ Pour représenter les -uplets
➻ C’est un objet constitué de composants nommés
pouvant être de types différents
➻ En Pascal Enregistrement=Record
API2 - LST«A» – p.4/42
Enregistrement
Enregistrement = structure = article = record
➻ Pour représenter les -uplets
➻ C’est un objet constitué de composants nommés
pouvant être de types différents
➻ En Pascal Enregistrement=Record
Syntaxe :
type
<nom_du_type> = record
<nom_du_champ_1> : <type_du_champ_1> ;
<nom_du_champ_2> : <type_du_champ_2> ;
...
end {record} ;
API2 - LST«A» – p.4/42
Déclaration, Accès
type T_HEURE
= 0..23 ;
T_MINUTE = 0..59 ;
T_SECONDE = 0..59 ;
T_HORAIRE = record
h : T_HEURE ;
m : T_MINUTE ;
s : T_SECONDE ;
end {record} ;
h1, h2 : T_HORAIRE ;
Ainsi, le type T_HORAIRE est
un type composé de champs
de types différents.
Les champs du type T_HORAIRE sont nommés h, m et s.
API2 - LST«A» – p.5/42
Déclaration, Accès
On peut faire les opérations suivantes :
var h1,h2 : T_HORAIRE ;
|with h1 do begin
h1.h := 10 ;
| h := 10 ;
h1.m := 35 ;
| m := 35 ;
h1.s := 20 ;
| s := 20 ;
|end ;
h2 := h1 ;
API2 - LST«A» – p.6/42
Déclaration, Accès
On peut faire les opérations suivantes :
var h1,h2 : T_HORAIRE ;
|with h1 do begin
h1.h := 10 ;
| h := 10 ;
h1.m := 35 ;
| m := 35 ;
h1.s := 20 ;
| s := 20 ;
|end ;
h2 := h1 ;
➻ On accède aux champs avec la notation pointée
API2 - LST«A» – p.6/42
Déclaration, Accès
On peut faire les opérations suivantes :
var h1,h2 : T_HORAIRE ;
|with h1 do begin
h1.h := 10 ;
| h := 10 ;
h1.m := 35 ;
| m := 35 ;
h1.s := 20 ;
| s := 20 ;
|end ;
h2 := h1 ;
➻ On accède aux champs avec la notation pointée
➻ On peut affecter un enregistrement en bloc
API2 - LST«A» – p.6/42
Déclaration, Accès
On peut faire les opérations suivantes :
var h1,h2 : T_HORAIRE ;
|with h1 do begin
h1.h := 10 ;
| h := 10 ;
h1.m := 35 ;
| m := 35 ;
h1.s := 20 ;
| s := 20 ;
|end ;
h2 := h1 ;
➻ On accède aux champs avec la notation pointée
➻ On peut affecter un enregistrement en bloc
➻ On ne peut pas comparer 2 enregistrements
API2 - LST«A» – p.6/42
Déclaration, Accès
On peut faire les opérations suivantes :
var h1,h2 : T_HORAIRE ;
|with h1 do begin
h1.h := 10 ;
| h := 10 ;
h1.m := 35 ;
| m := 35 ;
h1.s := 20 ;
| s := 20 ;
|end ;
h2 := h1 ;
➻
➻
➻
➻
On accède aux champs avec la notation pointée
On peut affecter un enregistrement en bloc
On ne peut pas comparer 2 enregistrements
On évitera les types anonymes !
API2 - LST«A» – p.6/42
Déclaration de constante
On peut déclarer des constantes typées :
const
<nom_const> : <nom_du_type>=<valeur_const>;
API2 - LST«A» – p.7/42
Déclaration de constante
On peut déclarer des constantes typées :
const
<nom_const> : <nom_du_type>=<valeur_const>;
Exemple :
const
DEPART : T_HORAIRE = (h:8; m:30; s:0);
API2 - LST«A» – p.7/42
Déclaration de constante
On peut déclarer des constantes typées :
const
<nom_const> : <nom_du_type>=<valeur_const>;
Exemple :
const
DEPART : T_HORAIRE = (h:8; m:30; s:0);
Attention ! si h est une variable, on ne peut pas écrire
h := (h:10 ; m:0; s:0) ;
API2 - LST«A» – p.7/42
Un autre exemple
type T_JOURS = (Lundi, Mardi, Mercredi, Jeudi,
Vendredi, Samedi, Dimanche) ;
T_QUANTIEME = 1..31 ;
T_MOIS = (Janvier, Fevrier, Mars, Avril,
Mai, Juin, Juillet, Aout,
Septembre, Octobre, Novembre,
Decembre);
T_ANNEE = Cardinal ;
T_DATE = record
jour
: T_JOUR ;
quantieme : T_QUANTIEME ;
mois
: T_MOIS ;
annee
: T_ANNEE ;
end {record} ;
API2 - LST«A» – p.8/42
Article avec partie variable
➻ Une partie de la structure est fixée pour tous les les
objets
API2 - LST«A» – p.9/42
Article avec partie variable
➻ Une partie de la structure est fixée pour tous les les
objets
➻ Le reste peut prendre plusieurs formes différentes.
D’où les articles avec partie variable
API2 - LST«A» – p.9/42
Article avec partie variable
➻ Une partie de la structure est fixée pour tous les les
objets
➻ Le reste peut prendre plusieurs formes différentes.
D’où les articles avec partie variable
➻ Le choix entre les différentes alternatives est gouverné
par la valeur d’un discriminant
API2 - LST«A» – p.9/42
Article avec partie variable
➻ Une partie de la structure est fixée pour tous les les
objets
➻ Le reste peut prendre plusieurs formes différentes.
D’où les articles avec partie variable
➻ Le choix entre les différentes alternatives est gouverné
par la valeur d’un discriminant
➻ La partie variable ressemble à une instruction case
API2 - LST«A» – p.9/42
Article avec partie variable
➻ Une partie de la structure est fixée pour tous les les
objets
➻ Le reste peut prendre plusieurs formes différentes.
D’où les articles avec partie variable
➻ Le choix entre les différentes alternatives est gouverné
par la valeur d’un discriminant
➻ La partie variable ressemble à une instruction case
➻ Elle vient après les autres champs
API2 - LST«A» – p.9/42
Syntaxe
type
<nom_du_type> = record
<nom_champ_1> : <nom_type_1> ;
...
<nom_champ_n> : <nom_type_n> ;
case selecteur : <type_scalaire> of
<liste_const_1> : (<variante_1>) ;
...
<liste_const_n> : (<variante_n>) ;
end ;
<variante_k> est de la forme :
<nom_champ_1> : <nom_type_1> ;
...
<nom_champ_m> : <nom_type_m> ;
API2 - LST«A» – p.10/42
Exemple
type
T_NOM = String[20] ;
T_GENRE = (Masculin, Feminin) ;
T_INDIVIDU = record
nom
: T_NOM ;
naissance : T_DATE ; // date de naissance
case sexe : T_GENRE of
Masculin : (Barbu : boolean) ;
Feminin : (Enfants : Cardinal) ;
end ;
API2 - LST«A» – p.11/42
Déclaration de constante
const TOTO : T_INDIVIDU
= (nom
: ’Toto’ ;
naissance : (jour
quantieme
mois
annee
sexe
: Masculin ;
barbu
: true
) ;
:
:
:
:
VENDREDI;
11 ;
MARS ;
2005) ;
API2 - LST«A» – p.12/42
Utilisation
procedure putIndividu(const ind: T_INDIVIDU) ;
begin
with ind do begin
write(nom,’ : ’) ;
with naissance do begin
putJour(jour); write(quantieme,’ ’);
putMois(mois); write(annee) ;
end ; // with
writeln ;
case sexe of
Masculin : begin
write(’Barbu: ’) ;
if barbu then write(’oui’)
else write(’non’);
end ;
Feminin : write(’Enfants: ’,enfants) ;
end ; // case
end ; // with
writeln ;
end ; // putIndividu
API2 - LST«A» – p.13/42
Struct. de données dynamiques
➻ La définition et l’utilisation d’un type de données
(TD) permet de fixer une fois pour toutes le domaine
des valeurs possibles pour les variables et par
conséquent leur format en mémoire. On a ainsi des
valeurs statiques.
API2 - LST«A» – p.14/42
Struct. de données dynamiques
➻ La définition et l’utilisation d’un type de données
(TD) permet de fixer une fois pour toutes le domaine
des valeurs possibles pour les variables et par
conséquent leur format en mémoire. On a ainsi des
valeurs statiques.
➻ Si les valeurs et les structures des variables changent
pendant le calcul, elles deviennent dynamiques.
API2 - LST«A» – p.14/42
Struct. de données dynamiques
➻ La définition et l’utilisation d’un type de données
(TD) permet de fixer une fois pour toutes le domaine
des valeurs possibles pour les variables et par
conséquent leur format en mémoire. On a ainsi des
valeurs statiques.
➻ Si les valeurs et les structures des variables changent
pendant le calcul, elles deviennent dynamiques.
➻ Les composants de telles structures sont à un niveau
de résolution donné statiques.
API2 - LST«A» – p.14/42
Algorithmes
Données
A LGORITHMES
instruction élémentaire
D ONNÉES
type scalaire (non structuré)
(non structurée)
briques de base pour
instructions composées
types de données composites
API2 - LST«A» – p.15/42
Algorithmes
Données
A LGORITHMES
instruction élémentaire
D ONNÉES
type scalaire (non structuré)
(non structurée)
briques de base pour
instructions composées
A LGORITHMES
instructions composées
types de données composites
D ONNÉES
type enregistrement
nombre fini de composants qui peuvent être de natures différentes
API2 - LST«A» – p.15/42
Algorithmes
Données
A LGORITHMES
for (répétition un nombre fini et
connu de fois)
D ONNÉES
type tableau (nombre fini et
connu d’éléments de même
type)
API2 - LST«A» – p.16/42
Algorithmes
Données
A LGORITHMES
for (répétition un nombre fini et
connu de fois)
D ONNÉES
type tableau (nombre fini et
connu d’éléments de même
type)
A LGORITHMES
D ONNÉES
choix parmi deux ou plusieurs
if ou case
type enregistrement avec
variante
API2 - LST«A» – p.16/42
Algorithmes
A LGORITHMES
Données
D ONNÉES
répétition un nombre initialement inconnu de fois
while ou loop
suite ou fichier
forme simple pour construire
des types de cardinalité “infinie"
API2 - LST«A» – p.17/42
Algorithmes
Données
A LGORITHMES
D ONNÉES
répétition un nombre initialement inconnu de fois
while ou loop
suite ou fichier
forme simple pour construire
des types de cardinalité “infinie"
A LGORITHMES
D ONNÉES
récursivité
Procédure directement
Types de données
ou indirectement récursive
récursifs
API2 - LST«A» – p.17/42
Algorithmes
Données
A LGORITHMES
D ONNÉES
répétition un nombre initialement inconnu de fois
while ou loop
suite ou fichier
forme simple pour construire
des types de cardinalité “infinie"
A LGORITHMES
D ONNÉES
récursivité
Procédure directement
Types de données
ou indirectement récursive
récursifs
Pour définir les types récursifs, on utilisera les pointeurs.
API2 - LST«A» – p.17/42
Pointeurs
➻ La propriété caractéristique des Structures de Données
Récursives (SDR) est leur faculté de varier de taille.
API2 - LST«A» – p.18/42
Pointeurs
➻ La propriété caractéristique des Structures de Données
Récursives (SDR) est leur faculté de varier de taille.
➻ On n’affecte pas de quantité fixe de mémoire à une
SDR. Donc le compilateur ne peut pas associer une
adresse spécifique aux composants de telles variables.
API2 - LST«A» – p.18/42
Pointeurs
➻ La propriété caractéristique des Structures de Données
Récursives (SDR) est leur faculté de varier de taille.
➻ On n’affecte pas de quantité fixe de mémoire à une
SDR. Donc le compilateur ne peut pas associer une
adresse spécifique aux composants de telles variables.
➻ La technique utilisée est l’allocation dynamique de
mémoire.
API2 - LST«A» – p.18/42
Pointeurs
➻ La propriété caractéristique des Structures de Données
Récursives (SDR) est leur faculté de varier de taille.
➻ On n’affecte pas de quantité fixe de mémoire à une
SDR. Donc le compilateur ne peut pas associer une
adresse spécifique aux composants de telles variables.
➻ La technique utilisée est l’allocation dynamique de
mémoire.
➻ Une quantité fixe de mémoire, juste assez pour
contenir l’adresse du composant dynamiquement
alloué, à la place du composant lui-même.
API2 - LST«A» – p.18/42
Les pointeurs en Pascal
➻ Un pointeur est une variable qui désigne une adresse
mémoire.
API2 - LST«A» – p.19/42
Les pointeurs en Pascal
➻ Un pointeur est une variable qui désigne une adresse
mémoire.
➻ Quand un pointeur contient l’adresse d’une autre
variable, on dit qu’il pointe sur l’emplacement en
mémoire de cette variable.
API2 - LST«A» – p.19/42
Les pointeurs en Pascal
➻ Un pointeur est une variable qui désigne une adresse
mémoire.
➻ Quand un pointeur contient l’adresse d’une autre
variable, on dit qu’il pointe sur l’emplacement en
mémoire de cette variable.
➻ Un pointeur de tableau contient l’adresse du premier
élément du tableau.
API2 - LST«A» – p.19/42
Les pointeurs en Pascal
➻ Un pointeur est une variable qui désigne une adresse
mémoire.
➻ Quand un pointeur contient l’adresse d’une autre
variable, on dit qu’il pointe sur l’emplacement en
mémoire de cette variable.
➻ Un pointeur de tableau contient l’adresse du premier
élément du tableau.
➻ Les pointeurs sont typés pour indiquer le type de
données stockées à l’adresse qu’ils contiennent.
API2 - LST«A» – p.19/42
Les pointeurs en Pascal
➻ Un pointeur est une variable qui désigne une adresse
mémoire.
➻ Quand un pointeur contient l’adresse d’une autre
variable, on dit qu’il pointe sur l’emplacement en
mémoire de cette variable.
➻ Un pointeur de tableau contient l’adresse du premier
élément du tableau.
➻ Les pointeurs sont typés pour indiquer le type de
données stockées à l’adresse qu’ils contiennent.
➻ Les pointeurs occupent 4 octets en mémoire.
API2 - LST«A» – p.19/42
Comprendre les pointeurs
Soit le code suivant :
var
X, Y: Integer ; // variables entières
P: ^Integer ;
// P pointe sur un entier
begin
X := 3 ;
// X reçoit la valeur 3
P := @X ; // P contient l’adresse de X
Y := P^ ; // Y reçoit la valeur contenue
// à l’adresse P
end ;
API2 - LST«A» – p.20/42
Comprendre les pointeurs
➻ @ permet d’avoir l’adresse d’une variable.
API2 - LST«A» – p.21/42
Comprendre les pointeurs
➻ @ permet d’avoir l’adresse d’une variable.
➻ mis devant un nom de type permet de définir un type
pointeur sur des variables de ce type.
nom_Type_Defini
API2 - LST«A» – p.21/42
Comprendre les pointeurs
➻ @ permet d’avoir l’adresse d’une variable.
➻ mis devant un nom de type permet de définir un type
pointeur sur des variables de ce type.
➻
nom_Type_Defini
mis après une varaible pointeur, P , il déréférence le
pointeur : il renvoie la valeur contenue à l’adresse
contenue dans le pointeur.
API2 - LST«A» – p.21/42
Comprendre les pointeurs
➻ @ permet d’avoir l’adresse d’une variable.
➻ mis devant un nom de type permet de définir un type
pointeur sur des variables de ce type.
➻
nom_Type_Defini
mis après une varaible pointeur, P , il déréférence le
pointeur : il renvoie la valeur contenue à l’adresse
contenue dans le pointeur.
➻ Avec la déclaration :
type nom_Type_Ptr = type_Defini ;
Les valeurs de type nom_Type_Ptr sont des pointeurs
vers des données de type type_Defini.
API2 - LST«A» – p.21/42
Comprendre les pointeurs
➻ @ permet d’avoir l’adresse d’une variable.
➻ mis devant un nom de type permet de définir un type
pointeur sur des variables de ce type.
➻
nom_Type_Defini
mis après une varaible pointeur, P , il déréférence le
pointeur : il renvoie la valeur contenue à l’adresse
contenue dans le pointeur.
➻ Avec la déclaration :
type nom_Type_Ptr = type_Defini ;
Les valeurs de type nom_Type_Ptr sont des pointeurs
vers des données de type type_Defini.
➻ Les valeurs de type pointeur sont générées chaque fois
qu’un élément de donnée est alloué dynamiquement.
API2 - LST«A» – p.21/42
Pointeurs : Création
➻ Pour créer une donnée pointée, de type
nom_Type_Ptr, on utilise la procédure new :
new(P) ;
API2 - LST«A» – p.22/42
Pointeurs : Création
➻ Pour créer une donnée pointée, de type
nom_Type_Ptr, on utilise la procédure new :
new(P) ;
➻ Cette procédure alloue effectivement une variable de
type type_Defini et affecte le pointeur désignant
cette variable à P.
API2 - LST«A» – p.22/42
Pointeurs : Création
➻ Pour créer une donnée pointée, de type
nom_Type_Ptr, on utilise la procédure new :
new(P) ;
➻ Cette procédure alloue effectivement une variable de
type type_Defini et affecte le pointeur désignant
cette variable à P.
➻ On étend le domaine des valeurs de tous les types
pointeurs par une valeur unique qui ne pointe sur
aucun élément : nil.
API2 - LST«A» – p.22/42
Pointeurs : Création
➻ Pour créer une donnée pointée, de type
nom_Type_Ptr, on utilise la procédure new :
new(P) ;
➻ Cette procédure alloue effectivement une variable de
type type_Defini et affecte le pointeur désignant
cette variable à P.
➻ On étend le domaine des valeurs de tous les types
pointeurs par une valeur unique qui ne pointe sur
aucun élément : nil.
➻ On peut donc engendrer des structures finies sans
avoir besoin de la présence explicite de variantes dans
leur déclaration (récursive).
API2 - LST«A» – p.22/42
Exemple
type
PtrMonome = ^Monome ;
Monome = record
coef : Real;
// coefficient
deg : Integer ; // degré
suiv : PtrMonome ;
end; // record
procedure getMonome(out M: PtrMonome) ;
begin
new(P) ;
with P^ do begin
write(’Coefficient: ’) ; readln(coef) ;
write(’Degre: ’) ;
readln(deg) ;
suiv := nil ;
end; // with
end; // getMonome
API2 - LST«A» – p.23/42
Pointeurs : Restitution
➻ Il peut y avoir ou non un ramasse-miettes. Quoiqu’il
en soit, on peut préférer faire notre propre ménage.
API2 - LST«A» – p.24/42
Pointeurs : Restitution
➻ Il peut y avoir ou non un ramasse-miettes. Quoiqu’il
en soit, on peut préférer faire notre propre ménage.
➻ On peut le réaliser au moyen de la procédure
dispose
API2 - LST«A» – p.24/42
Pointeurs : Restitution
➻ Il peut y avoir ou non un ramasse-miettes. Quoiqu’il
en soit, on peut préférer faire notre propre ménage.
➻ On peut le réaliser au moyen de la procédure
dispose
➻ L’instruction dispose(P) libère la place pointée par
P.
API2 - LST«A» – p.24/42
Pointeurs : Restitution
➻ Il peut y avoir ou non un ramasse-miettes. Quoiqu’il
en soit, on peut préférer faire notre propre ménage.
➻ On peut le réaliser au moyen de la procédure
dispose
➻ L’instruction dispose(P) libère la place pointée par
P.
➻ Après un appel à dispose, la valeur de P est
indéterminée. P n’est pas mise à nil.
API2 - LST«A» – p.24/42
Pointeurs : Restitution
➻ Les deux procédures new et dispose utilisent une
zone mémoire appelée TAS.
API2 - LST«A» – p.25/42
Pointeurs : Restitution
➻ Les deux procédures new et dispose utilisent une
zone mémoire appelée TAS.
➻ new prend une place du TAS et dispose restitue une
place au TAS.
API2 - LST«A» – p.25/42
Pointeurs : Restitution
➻ Les deux procédures new et dispose utilisent une
zone mémoire appelée TAS.
➻ new prend une place du TAS et dispose restitue une
place au TAS.
➻ Ce «TAS» cessera d’exister quand on sera hors de la
portée du type poiteur.
API2 - LST«A» – p.25/42
Pointeurs : Restitution
➻ Les deux procédures new et dispose utilisent une
zone mémoire appelée TAS.
➻ new prend une place du TAS et dispose restitue une
place au TAS.
➻ Ce «TAS» cessera d’exister quand on sera hors de la
portée du type poiteur.
➻ Le programmeur doit gérer l’allocation-libération de
la place mais le système s’occupe lui-même de la
gestion interne du TAS.
API2 - LST«A» – p.25/42
Listes chaînées en Delphi
➻ On peut créer une séquence d’éléments liés entre-eux
et tels que chaque élément contient
API2 - LST«A» – p.26/42
Listes chaînées en Delphi
➻ On peut créer une séquence d’éléments liés entre-eux
et tels que chaque élément contient
➠ une partie utile : l’information proprement-dite
API2 - LST«A» – p.26/42
Listes chaînées en Delphi
➻ On peut créer une séquence d’éléments liés entre-eux
et tels que chaque élément contient
➠ une partie utile : l’information proprement-dite
➠ un lien vers l’élément suivant (s’il existe) : ce lien
est l’adresse de l’élément suivant.
API2 - LST«A» – p.26/42
Listes chaînées en Delphi
➻ On peut créer une séquence d’éléments liés entre-eux
et tels que chaque élément contient
➠ une partie utile : l’information proprement-dite
➠ un lien vers l’élément suivant (s’il existe) : ce lien
est l’adresse de l’élément suivant.
➻ Pour désigner une liste, il suffit d’avoir l’adresse de
son premier élément (tête de liste).
API2 - LST«A» – p.26/42
Listes chaînées en Delphi
➻ On peut créer une séquence d’éléments liés entre-eux
et tels que chaque élément contient
➠ une partie utile : l’information proprement-dite
➠ un lien vers l’élément suivant (s’il existe) : ce lien
est l’adresse de l’élément suivant.
➻ Pour désigner une liste, il suffit d’avoir l’adresse de
son premier élément (tête de liste).
➻ De ce premier élément, on peut consulter,
séquentiellement, tous les autres éléments.
API2 - LST«A» – p.26/42
Exemple 1
Une liste d’entiers :
type PtrNoeud = ^Noeud ;
Noeud = record
info : Integer ; // par exemple
suiv : PtrNoeud;
end ;
Liste = PtrNoeud ;
var
L
P: Liste ;
1
2
3
4
nil
API2 - LST«A» – p.27/42
Exemple 2
Un polynôme à coefficients réels :
type PtrMonome = ^Monome ;
Monome = record
coef : Real ;
// coefficient
deg : Integer ;// degré
suiv : PtrMonome ;
end ;
Polynome = PtrMonome ;
var P: Polynome ;
3.5
1
5.1
3
1.0
5
nil
0
2.0
P
API2 - LST«A» – p.28/42
Ajout en tête
➻ On se donne une liste (i.e. son pointeur de tête L)
API2 - LST«A» – p.29/42
Ajout en tête
➻ On se donne une liste (i.e. son pointeur de tête L)
➻ On se donne un élément donné par un pointeur P
API2 - LST«A» – p.29/42
Ajout en tête
➻ On se donne une liste (i.e. son pointeur de tête L)
➻ On se donne un élément donné par un pointeur P
➻ Il s’agit de mettre P en tête de liste
API2 - LST«A» – p.29/42
Ajout en tête
➻ On se donne une liste (i.e. son pointeur de tête L)
➻ On se donne un élément donné par un pointeur P
➻ Il s’agit de mettre P en tête de liste
L
P
1
2
3
4
nil
0
API2 - LST«A» – p.29/42
Ajout en tête
➻ On se donne une liste (i.e. son pointeur de tête L)
➻ On se donne un élément donné par un pointeur P
➻ Il s’agit de mettre P en tête de liste
L
1
2
3
4
nil
1
P
0
API2 - LST«A» – p.29/42
Ajout en tête
➻ On se donne une liste (i.e. son pointeur de tête L)
➻ On se donne un élément donné par un pointeur P
➻ Il s’agit de mettre P en tête de liste
L
1
2
2
3
4
nil
1
P
0
API2 - LST«A» – p.29/42
Ajout en tête
➻ On se donne une liste (i.e. son pointeur de tête L)
➻ On se donne un élément donné par un pointeur P
➻ Il s’agit de mettre P en tête de liste
L
1
2
P
3
4
nil
1
P
L
2
0
0
1
2
3
4
nil
API2 - LST«A» – p.29/42
Ajout en tête
type PtrNoeud = ^Noeud ;
Noeud = record
info : Integer ;
suiv : PtrNoeud
end; // record
List = PtrNoeud ;
procedure headAdd(var L:list;var P:PtrNoeud);
begin
P^.suiv := L ;
L := P ;
end; // headAdd
API2 - LST«A» – p.30/42
Ajout en queue
➻ L désigne la tête de la liste et Q en désigne la queue.
API2 - LST«A» – p.31/42
Ajout en queue
➻ L désigne la tête de la liste et Q en désigne la queue.
➻ On se donne un élément pointé par P.
API2 - LST«A» – p.31/42
Ajout en queue
➻ L désigne la tête de la liste et Q en désigne la queue.
➻ On se donne un élément pointé par P.
➻ Il s’agit de mettre P en queue de liste
API2 - LST«A» – p.31/42
Ajout en queue
➻ L désigne la tête de la liste et Q en désigne la queue.
➻ On se donne un élément pointé par P.
➻ Il s’agit de mettre P en queue de liste
Q
L
1
2
3
P
4
nil
0
nil
API2 - LST«A» – p.31/42
Ajout en queue
➻ L désigne la tête de la liste et Q en désigne la queue.
➻ On se donne un élément pointé par P.
➻ Il s’agit de mettre P en queue de liste
Q
L
1
2
3
P
4
nil
0
nil
API2 - LST«A» – p.31/42
Ajout en queue
➻ L désigne la tête de la liste et Q en désigne la queue.
➻ On se donne un élément pointé par P.
➻ Il s’agit de mettre P en queue de liste
.
L
1
2
3
4
nil
Q
P
0
nil
API2 - LST«A» – p.31/42
Ajout en queue
➻ L désigne la tête de la liste et Q en désigne la queue.
➻ On se donne un élément pointé par P.
➻ Il s’agit de mettre P en queue de liste
.
L
1
2
3
4
nil
Q
P
0
nil
.
L
1
2
3
4
Q
P
0
nil
API2 - LST«A» – p.31/42
Ajout en queue
procedure endAdd(var L:List;
var Q:PtrNoeud; P:PtrNoeud);
begin
Q^.suiv := P ;
Q := P ;
end; // endAdd
➻ L est la tête de la liste
➻ Q est la queue de la liste
➻ P est le nouvel élément
NB pour ne pas devoir parcourir à chaque fois la liste, on
maintient un pointeur sur la queue de celle-ci.
API2 - LST«A» – p.32/42
Liste : création
➻ On part d’une liste vide
➻ On fait des ajouts en tête
procedure createListHead(out L: list) ;
var P: PtrNoeud ;
begin
L := nil ;
// liste vide
getNoeud(P) ; // saisie d’un noeud
while P^.info <> -1 do begin
headAdd(L,P) ;
getNoeud(P) ;
end; //while
end; // createListHead
API2 - LST«A» – p.33/42
Liste : création
➻ On part d’une liste vide
➻ On fait des ajouts en queue
procedure createListEnd(out L: list) ;
var P,T: PtrNoeud ;
begin
L := nil ;
// liste vide
getNoeud(P) ; // saisie d’un noeud
while P^.info <> -1 do begin
if L = nil then begin
L := P ; T := P ;
end else endAdd(L,T,P) ;
getNoeud(P) ;
end; //while
end; // createListEnd
API2 - LST«A» – p.34/42
Liste : opérations
➻ Sur les listes, on peut être amené à faire les opérations
suivantes :
API2 - LST«A» – p.35/42
Liste : opérations
➻ Sur les listes, on peut être amené à faire les opérations
suivantes :
➠ Ajouter un élément après un élément donné par
son adresse
API2 - LST«A» – p.35/42
Liste : opérations
➻ Sur les listes, on peut être amené à faire les opérations
suivantes :
➠ Ajouter un élément après un élément donné par
son adresse
➠ Supprimer l’élément suivant un élément donné par
son adresse
API2 - LST«A» – p.35/42
Liste : opérations
➻ Sur les listes, on peut être amené à faire les opérations
suivantes :
➠ Ajouter un élément après un élément donné par
son adresse
➠ Supprimer l’élément suivant un élément donné par
son adresse
➠ Appliquer un traitement à tous les éléments d’une
liste
API2 - LST«A» – p.35/42
Liste : opérations
➻ Sur les listes, on peut être amené à faire les opérations
suivantes :
➠ Ajouter un élément après un élément donné par
son adresse
➠ Supprimer l’élément suivant un élément donné par
son adresse
➠ Appliquer un traitement à tous les éléments d’une
liste
➠ Chercher un élément dans une liste
API2 - LST«A» – p.35/42
Liste : opérations
➻ Sur les listes, on peut être amené à faire les opérations
suivantes :
➠ Ajouter un élément après un élément donné par
son adresse
➠ Supprimer l’élément suivant un élément donné par
son adresse
➠ Appliquer un traitement à tous les éléments d’une
liste
➠ Chercher un élément dans une liste
➠
API2 - LST«A» – p.35/42
Ajouter un élément
On veut insérer l’élément pointé par P, après l’élément
pointé par Q dans la liste L.
API2 - LST«A» – p.36/42
Ajouter un élément
On veut insérer l’élément pointé par P, après l’élément
pointé par Q dans la liste L.
P
0
nil
Q
L
1
2
3
4
nil
API2 - LST«A» – p.36/42
Ajouter un élément
On veut insérer l’élément pointé par P, après l’élément
pointé par Q dans la liste L.
P
0
1
Q
L
1
2
3
4
nil
API2 - LST«A» – p.36/42
Ajouter un élément
On veut insérer l’élément pointé par P, après l’élément
pointé par Q dans la liste L.
P
Q
L
1
2
0
1
2
3
4
nil
API2 - LST«A» – p.36/42
Ajouter un élément
On veut insérer l’élément pointé par P, après l’élément
pointé par Q dans la liste L.
P
0
Q
L
1
2
1
2
3
4
nil
Q
L
1
2
3
0
4
nil
API2 - LST«A» – p.36/42
Supprimer un élément
➻ On veut supprimer l’élément suivant l’élément pointé
par Q.
API2 - LST«A» – p.37/42
Supprimer un élément
➻ On veut supprimer l’élément suivant l’élément pointé
par Q.
➻ On l’affecte à une variable temporaire R
API2 - LST«A» – p.37/42
Supprimer un élément
➻ On veut supprimer l’élément suivant l’élément pointé
par Q.
➻ On l’affecte à une variable temporaire R
➻ On libère cette variable ensuite
API2 - LST«A» – p.37/42
Supprimer un élément
➻ On veut supprimer l’élément suivant l’élément pointé
par Q.
➻ On l’affecte à une variable temporaire R
➻ On libère cette variable ensuite
Q
L
1
2
3
4
nil
API2 - LST«A» – p.37/42
Supprimer un élément
➻ On veut supprimer l’élément suivant l’élément pointé
par Q.
➻ On l’affecte à une variable temporaire R
➻ On libère cette variable ensuite
Q
L
1
2
3
4
nil
1
R
API2 - LST«A» – p.37/42
Supprimer un élément
➻ On veut supprimer l’élément suivant l’élément pointé
par Q.
➻ On l’affecte à une variable temporaire R
➻ On libère cette variable ensuite
Q
L
1
2
2
3
4
nil
1
R
API2 - LST«A» – p.37/42
Supprimer un élément
➻ On veut supprimer l’élément suivant l’élément pointé
par Q.
➻ On l’affecte à une variable temporaire R
➻ On libère cette variable ensuite
Q
L
1
2
2
3
4
nil
1
R
Q
L
1
2
4
nil
API2 - LST«A» – p.37/42
Appliquer un traitement
AppliquerTraitement(L):
begin
P := premier(L) ;
while not estEnFin(P) do begin
traiter(P) ;
next(P) ;
end; // while
end;
// AppliquerTraitement
➻
➻
➻
➻
premier retourne la tête de liste
estEnFin indique si la fin de liste est atteinte
traiter applique un traitement au nœud P
next avance le pointeur sur l’élément suivant
API2 - LST«A» – p.38/42
Rechercher un élément
recherche(P,L):
begin
Q := premier(L) ;
trouve := false ;
while not trouve and
not estEnFin(Q) do begin
if egal(Q,P) then trouve := true
else Next(Q) ;
end; // while
retourner(trouve)
end;
// recherche
API2 - LST«A» – p.39/42
Extension : bidirectionnelles
➻ Dans les listes simples, on ne peut pas revenir en
arrière, car on n’a pas l’adresse du précédent.
API2 - LST«A» – p.40/42
Extension : bidirectionnelles
➻ Dans les listes simples, on ne peut pas revenir en
arrière, car on n’a pas l’adresse du précédent.
➻ Les listes bidirectionnelles n’ont pas cet inconvénient :
chaque élément possède deux liens
API2 - LST«A» – p.40/42
Extension : bidirectionnelles
➻ Dans les listes simples, on ne peut pas revenir en
arrière, car on n’a pas l’adresse du précédent.
➻ Les listes bidirectionnelles n’ont pas cet inconvénient :
chaque élément possède deux liens
➠ un vers son successeur
API2 - LST«A» – p.40/42
Extension : bidirectionnelles
➻ Dans les listes simples, on ne peut pas revenir en
arrière, car on n’a pas l’adresse du précédent.
➻ Les listes bidirectionnelles n’ont pas cet inconvénient :
chaque élément possède deux liens
➠ un vers son successeur
➠ un vers son prédécesseur
API2 - LST«A» – p.40/42
Extension : bidirectionnelles
➻ Dans les listes simples, on ne peut pas revenir en
arrière, car on n’a pas l’adresse du précédent.
➻ Les listes bidirectionnelles n’ont pas cet inconvénient :
chaque élément possède deux liens
➠ un vers son successeur
➠ un vers son prédécesseur
L
nil
nil
API2 - LST«A» – p.40/42
Exemple
type PtrChainon = ^Chainon
Chainon = record
info : Integer ; //
pred : PtrChainon ;
suiv : PtrChainon ;
end ;
Pour supprimer l’élément pointé par Q :
Q^.suiv^.pred := Q^.pred
Q^.pred^.suiv := Q^.suiv
dispose(Q) ;
;
par exemple
;
;
API2 - LST«A» – p.41/42
Extension : circulaires
➻ Ce sont des listes dans lesquelles le premier élément
est le suivant du dernier.
API2 - LST«A» – p.42/42
Extension : circulaires
➻ Ce sont des listes dans lesquelles le premier élément
est le suivant du dernier.
➻ Elles peuvent être bidirectionnelles.
API2 - LST«A» – p.42/42
Extension : circulaires
➻ Ce sont des listes dans lesquelles le premier élément
est le suivant du dernier.
➻ Elles peuvent être bidirectionnelles.
L
API2 - LST«A» – p.42/42
Extension : circulaires
➻ Ce sont des listes dans lesquelles le premier élément
est le suivant du dernier.
➻ Elles peuvent être bidirectionnelles.
L
API2 - LST«A» – p.42/42