Ch. 05 · Leçon 1
Les sous-programmes : analyse modulaire, procédures et fonctions
Ce que vous saurez faire
- →Décomposer un problème complexe en sous-problèmes (analyse modulaire)
- →Distinguer une procédure d'une fonction et choisir le sous-programme adapté
- →Déclarer correctement les objets locaux et globaux d'un sous-programme
- →Différencier le passage de paramètres par valeur et par variable
- →Écrire et traduire des sous-programmes en Pascal
id: 33-210-sous-programmes slug: 33-210-sous-programmes titre: 'Les sous-programmes : analyse modulaire, procédures et fonctions' chapitre: 5 chapitre_titre: Les sous-programmes lecon: 1 niveau: 4eme-sci ordre: 1 prerequis: [] duree_estimee_min: 90 mots_cles:
- sous-programme
- procedure
- fonction
- analyse modulaire
- parametre formel
- parametre effectif
- passage par valeur
- passage par variable
- objet local
- objet global langages:
- analyse
- pascal objectifs:
- Décomposer un problème complexe en sous-problèmes (analyse modulaire)
- Distinguer une procédure d'une fonction et choisir le sous-programme adapté
- Déclarer correctement les objets locaux et globaux d'un sous-programme
- Différencier le passage de paramètres par valeur et par variable
- Écrire et traduire des sous-programmes en Pascal status: published source_pdf: 33_210.pdf source_pages:
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33 kind: cours
Les sous-programmes
Leçon 1 — L'analyse modulaire
Introduction
Afin de faciliter la résolution d'un problème complexe et/ou de grande taille, on doit le décomposer en sous-problèmes indépendants et de taille réduite.
Définition de l'analyse modulaire
Intérêts de l'analyse modulaire
- Plus d'organisation en séparant les difficultés et les tâches.
- S'occuper d'un seul problème à la fois.
- En cas d'erreur, la division en modules permet de savoir quel module corriger.
- Plus facile à faire évoluer.
- Permet d'éviter la répétition d'un même traitement dans un programme.
Notion de sous-programme
Exemple d'analyse modulaire : l'étude d'une fonction mathématique.
Leçon 2 — Les procédures
Définition
Vocabulaire et syntaxe
En analyse :
DEF PROC nom (paramètres formels : type)
Résultat =
Traitement
Fin nom
En algorithme :
0) DEF PROC nom (paramètres formels : type)
1) Traitement
2) Fin nom
En analyse :
DEF PROC nom (paramètres formels : type)
Résultat =
Traitement
Fin nom
En algorithme :
0) DEF PROC nom (paramètres formels : type)
1) Traitement
2) Fin nom
Procedure nom (paramètres formels : type) ;
Déclaration des variables locales ;
Begin
Traitement ;
End;
Appel d'une procédure
Proc nom_procédure (paramètres effectifs)
Activité — Permutation de deux entiers
Écrire un programme qui permet de saisir deux entiers a et b strictement positifs, puis de permuter leurs valeurs, et enfin de les afficher.
Voir le corrigé
Pour résoudre ce problème, on utilise les modules suivants : saisir, permuter et afficher.
Analyse du programme principal :
Nom : permutation
Résultat = PROC Afficher (a, b)
(a, b) = PROC Permuter (a, b)
(a, b) = PROC Saisir (a, b)
Fin Permutation
Tableau de Déclaration des Objets Globaux :
| Objet | Type/nature | Rôle |
|---|---|---|
| a, b | Entier | Entiers à saisir |
| Afficher, Permuter, Saisir | Procédures | Afficher, permuter et saisir (a et b) |
Algorithme de la procédure Afficher :
0) DEF Proc Afficher (a : entier, b : entier)
1) Ecrire("a=", a, " b=", b)
2) Fin Afficher
Algorithme de la procédure Saisir :
0) DEF PROC Saisir (VAR a : entier, VAR b : entier)
1) Répéter
Ecrire("a="), lire(a)
Ecrire("b="), lire(b)
Jusqu'à (a > 0) et (b > 0)
2) Fin Saisir
Algorithme de la procédure Permuter :
0) DEF Proc Permuter (VAR a : entier, VAR b : entier)
1) c ← a
2) a ← b
3) b ← c
4) Fin Permuter
T.D.O locaux de Permuter :
| Objet | Type/nature | Rôle |
|---|---|---|
| c | Entier | Variable intermédiaire |
Traduction Pascal :
Program permutation;
Uses wincrt;
Var a, b : integer; { objets globaux }
Procedure saisir(VAR a : integer; VAR b : integer);
Begin { passage par variable }
repeat
writeln('a='); readln(a);
writeln('b='); readln(b);
until (a > 0) and (b > 0);
End;
Procedure permuter(VAR x : integer; VAR y : integer);
Var c : integer; { objets locaux }
Begin
c := x;
x := y;
y := c;
End;
Procedure afficher(a : integer; b : integer);
Begin { passage par valeur }
writeln('a=', a, ' b=', b);
End;
Begin
saisir(a, b); { appel d'une procédure }
permuter(a, b);
afficher(a, b);
End.
Leçon 3 — Déclaration, accès aux objets et mode de transmission
Déclaration et accès aux objets
Accès aux objets : Tous les objets locaux d'un sous-programme sont inaccessibles :
- par le programme principal,
- par les sous-programmes déclarés au même niveau que le sous-programme considéré,
- par le sous-programme qui englobe les sous-programmes considérés.
Les paramètres et leur mode de transmission
On distingue deux types de paramètres :
Mode de passage des paramètres
Il existe 2 modes de passage des paramètres :
- le mode par valeur
- le mode par variable
Pour le cas d'une fonction, nous définissons seulement le mode par valeur.
Mode de passage par valeur
- Permet au programme appelant de transmettre une valeur au sous-programme appelé.
- Le transfert d'information est effectué dans un seul sens : du programme appelant vers le sous-programme appelé.
- Au moment de l'appel, la valeur du paramètre effectif est copiée dans la variable locale désignée par le paramètre formel correspondant.
Mode de passage par variable
- Le passage par variable permet au programme appelant de transmettre une valeur au sous-programme appelé et inversement.
- Dans l'entête de la procédure, on doit précéder les paramètres formels transmis par variable par le mot-clé VAR.
Leçon 4 — Les fonctions
Définition
Syntaxe — Déclaration d'une fonction
En analyse :
DEF FN nom (paramètres formels : type) : Résultat
Résultat =
Nom ← résultat calculé
Traitement
Fin nom
En algorithme :
0) DEF FN nom (paramètres formels : type) : Type_Resultat
1) Traitement
2) Nom ← résultat calculé
3) Fin Nom
En analyse :
DEF FN nom (paramètres formels : type) : Résultat
Résultat =
Nom ← résultat calculé
Traitement
Fin nom
En algorithme :
0) DEF FN nom (paramètres formels : type) : Type_Resultat
1) Traitement
2) Nom ← résultat calculé
3) Fin Nom
Function nom (paramètres formels : type) : Type_Resultat;
Déclaration des variables locales;
Begin
Traitement;
Nom := RésultatCalculé;
End;
Appel de la fonction
En analyse :
Y ← FN f(x) { x est un paramètre effectif }
TDO :
| Objet | Type/nature | Rôle |
|---|---|---|
| f | Fonction | f(x) = ... |
Les trois parties d'une fonction
- La partie entête : on y trouve son nom suivi entre parenthèses des paramètres en entrée et de leur mode de passage, puis du type du résultat.
- La partie déclarative : tous les objets locaux de la fonction y sont déclarés.
- La partie instruction : on y trouve les instructions propres à la fonction. Ces instructions sont exécutées à la demande de l'appelant par une instruction d'appel.
Transmission du résultat de la fonction
Une fonction possède un type, c'est celui du résultat qu'elle calcule.
On appelle une fonction en utilisant simplement son nom suivi de la liste des paramètres effectifs séparés par des virgules.
Un appel de fonction figure obligatoirement dans une expression sous la forme suivante :
V ← FN nom_de_la_fonction (liste des paramètres effectifs)
Exemple : y ← FN f(x)
Il doit y avoir nécessairement, dans la partie instruction de la fonction, au moins une affectation explicite ayant l'identificateur de la fonction à gauche du symbole d'affectation.
Définition d'une fonction — récapitulatif
Lors de l'utilisation d'une fonction, il faut :
- Spécifier le type de la fonction.
- Déclarer, si nécessaire, une variable locale de même type que la fonction (pour faire les calculs intermédiaires).
- Affecter le résultat de calcul de la fonction au nom de la fonction, obligatoirement avant la fin du bloc.
Mode de passage
Pour le cas de la fonction, on définit seulement le mode de passage par valeur.
Activité 2 — Calcul de puissance
Écrire un programme qui permet de saisir deux entiers x et y avec y ≤ 9, puis de calculer la puissance x^y, et enfin d'afficher le résultat.
Voir le corrigé
Pour résoudre ce problème, on utilise :
- une procédure
saisir(x, y) - une fonction
puissance(x, y)
Analyse du programme principal :
Nom : calcul
Résultat = Ecrire("X à la puissance y =", p)
p ← FN puissance(x, y)
(x, y) = PROC saisir(x, y)
Fin calcul
T.D.O Globaux :
| Objet | Type/Nature | Rôle |
|---|---|---|
| x, y | Entier | Entiers à saisir |
| p | Entier | Puissance à calculer |
| saisir | Procédure | Saisir x et y |
| puissance | Fonction | Calculer la puissance p |
Algorithme de la procédure saisir :
0) DEF PROC Saisir(var x, y : entier)
1) Répéter
Ecrire("x= "), lire(x)
Ecrire("y= "), lire(y)
Jusqu'à (x <= 9) et (y <= 9)
2) Fin saisir
Algorithme de la fonction puissance :
0) DEF FN puissance(x, y : entier) : entier
1) [m ← 1] Pour i de 1 à y faire
m ← m * x
FinPour
2) puissance ← m
3) Fin puissance
T.D.O Locaux :
| Objet | Type/Nature | Rôle |
|---|---|---|
| m | Entier | Puissance à calculer |
| i | Entier | Compteur |
Programme Pascal :
Program calcul;
Uses wincrt;
Var x, y : integer; p : longint;
Procedure saisir(var x, y : integer);
Begin
Repeat
writeln('x= '); readln(x);
writeln('y= '); readln(y);
Until (x <= 9) and (y <= 9);
End;
Function puissance(x, y : integer) : longint;
Var i : integer; m : longint;
Begin
m := 1;
For i := 1 to y do
m := m * x;
puissance := m;
End;
Begin
saisir(x, y);
p := puissance(x, y);
writeln('X à la puissance y =', p);
End.
Exercices d'application
Rappel sur la génération aléatoire (Hasard / random)
Exercice 1 — Maximum d'un tableau
Écrire un programme qui permet de :
- Saisir un entier
n(entre 2 et 20). - Remplir un tableau
Tau hasard parnentiers de valeurs entre 0 et 100. - Afficher les éléments de
T. - Afficher le maximum de
T.
Voir le corrigé
Modules nécessaires :
- procédure
Saisie(n): saisir la taille du tableau entre 2 et 20. - procédure
Remplit(T, n): remplirTpar n entiers au hasard (entre 0 et 100). - procédure
Affiche(T, n): afficher le tableauT. - fonction
Maxi(T, n): renvoyer le maximum du tableau.
Analyse du programme principal :
NOM : Maximum
Résultat = Ecrire("Le max est", Max)
Max ← FN Maxi(T, n)
Proc Affiche(T, n)
T = PROC Remplit(T, n)
n = PROC Saisie(n)
FIN Maximum
Tableau de déclaration des nouveaux types :
| TYPE |
|---|
| TAB = Tableau de 20 entiers |
T.D.O Globaux :
| Objet | Type/Nature |
|---|---|
| T | TAB |
| n, Max | Entier |
| Maxi | Fonction |
| Remplit, Saisie, Affiche | Procédures |
Algorithmes :
0) DEF PROC Saisie(VAR nb : entier)
1) Répéter
Ecrire("Donner n: "), lire(nb)
Jusqu'à nb dans [2..20]
2) FIN Saisie
0) DEF PROC Remplit(Var T : TAB, n : entier)
1) Pour i de 1 à n faire
T[i] ← Hazard(101)
Fin pour
2) FIN Remplit
0) DEF PROC Affiche(T : TAB, n : entier)
1) Pour i de 1 à n faire
Ecrire("L'entier n° ", i, " est ", T[i])
Fin pour
2) FIN Affiche
0) DEF FN Maxi(T : TAB, n : entier) : entier
1) Ma ← T[1]
2) Pour i de 2 à n faire
Si T[i] > Ma alors Ma ← T[i] FinSi
Fin pour
3) Maxi ← Ma
4) FIN Maxi
Programme Pascal :
program maximum;
uses wincrt;
type tab = array[1..20] of integer;
var n, max : integer; t : tab;
procedure saisie(var n : integer);
begin
repeat
write('donner un entier(entre 2 et 20):');
readln(n);
until (n >= 2) and (n <= 20);
end;
procedure remplit(var t : tab; n : integer);
var i : integer;
begin
RANDOMIZE;
for i := 1 to n do
t[i] := random(101);
end;
procedure Affiche(t : tab; n : integer);
var i : integer;
begin
for i := 1 to n do
writeln('T[', i, ']= ', t[i]);
end;
function maxi(t : tab; n : integer) : integer;
var i, ma : integer;
begin
ma := t[1];
for i := 2 to n do
if t[i] > ma then ma := t[i];
maxi := ma;
end;
begin
saisie(n);
remplit(t, n);
Affiche(t, n);
max := maxi(t, n);
writeln('le maximum est ', max);
end.
Exercice 2 — Tableau inversé et entiers pairs
Écrire un programme qui permet de saisir n entre 2 et 5, puis de remplir un tableau T par des valeurs au hasard entre 10 et 99, puis d'afficher le tableau en ordre inverse, et enfin de calculer et afficher le nombre d'entiers pairs dans T.
Voir le corrigé
program pairs;
uses wincrt;
type
tab = array[1..5] of integer;
var
n, nb : integer;
t : tab;
procedure saisir(var n : integer);
begin
repeat
write('n= '); readln(n);
until n in [2..5];
end;
procedure remplir(var t : tab; n : integer);
var i : integer;
begin
for i := 1 to n do
t[i] := random(90) + 10;
end;
procedure afficher(t : tab; n : integer);
var i : integer;
begin
for i := n downto 1 do writeln(t[i]);
end;
function calculer(t : tab; n : integer) : integer;
var nb, i : integer;
begin
nb := 0;
for i := 1 to n do
if t[i] mod 2 = 0 then nb := nb + 1;
calculer := nb;
end;
begin
saisir(n);
randomize;
remplir(t, n);
afficher(t, n);
nb := calculer(t, n);
writeln('le nombre d''entiers pairs est:', nb);
end.
Exercice 3 — Voyelles dans un tableau de lettres
Écrire un programme qui permet de saisir n entre 3 et 7, puis de remplir un tableau T de taille n par des lettres minuscules au hasard, puis d'afficher le tableau en ordre inverse, et enfin de calculer et afficher le nombre de voyelles dans T.
Voir le corrigé
program Voyelles;
uses wincrt;
type
tab = array[1..7] of char;
var
n, nbv : integer;
t : tab;
procedure saisir(var n : integer);
begin
repeat
write('n= '); readln(n);
until n in [3..7];
end;
procedure remplir(var t : tab; n : integer);
var i : integer;
begin
for i := 1 to n do
t[i] := chr(random(26) + 97);
end;
procedure afficher(t : tab; n : integer);
var i : integer;
begin
for i := n downto 1 do writeln(t[i]);
end;
function calcul(t : tab; n : integer) : integer;
var nbv, i : integer;
begin
nbv := 0;
for i := 1 to n do
if t[i] in ['a','e','y','u','i','o'] then nbv := nbv + 1;
calcul := nbv;
end;
begin
saisir(n);
randomize;
remplir(t, n);
afficher(t, n);
nbv := calcul(t, n);
writeln('Le nombre des voyelles est:', nbv);
end.
Exercice 4 — Produit scalaire de deux vecteurs
Écrire un programme qui permet de saisir n (avec n = 2 ou n = 3), puis de remplir 2 vecteurs t1 et t2 de taille n, puis de calculer et d'afficher le produit scalaire des deux vecteurs, et enfin d'afficher si ces deux vecteurs sont orthogonaux.
On rappelle que pour t1(x1, y1) et t2(x2, y2) : ps = x1*x2 + y1*y2.
(Deux vecteurs sont orthogonaux si leur produit scalaire est égal à zéro.)
Voir le corrigé
program produit;
uses wincrt;
type tab = array[1..3] of integer;
var t1, t2 : tab;
ps, n : integer;
procedure saisir(var n : integer);
begin
repeat
write('n= '); readln(n);
until (n = 2) or (n = 3);
end;
procedure remplir(var t : tab; n : integer);
var i : integer;
begin
for i := 1 to n do
begin
write('donner l''élément n°', i, '= '); readln(t[i]);
end;
end;
function calculer_ps(T1 : tab; T2 : tab; n : integer) : integer;
var ps, i : integer;
begin
ps := 0;
for i := 1 to n do
ps := ps + T1[i] * T2[i];
calculer_ps := ps;
end;
procedure afficher_dec(ps : integer);
begin
if ps = 0 then writeln('T1 et T2 sont orthogonaux')
else writeln('T1 et T2 ne sont pas orthogonaux');
end;
begin
saisir(n);
remplir(t1, n);
remplir(t2, n);
ps := calculer_ps(t1, t2, n);
writeln('Le produit scalaire est ', ps);
afficher_dec(ps);
end.
Exercice 5 — Extraction des pairs et impairs
Écrire un programme qui permet de remplir un tableau T de taille n par des entiers positifs, puis d'extraire les entiers pairs dans un tableau T1 et les entiers impairs dans un tableau T2, et enfin d'afficher les tableaux T1 et T2.
Voir le corrigé
Analyse du programme principal :
NOM : Parité
Résultat = Proc Afficher(T2, n2)
Proc Afficher(T1, n1)
(T1, n1, T2, n2) = Proc Extraire(T, n, T1, n1, T2, n2)
(T, n) = Proc Saisir(T, n)
FIN Parité
Type : TAB = Tableau de 10 entiers
T.D.O Globaux :
| Objet | Type/Nature | Rôle |
|---|---|---|
| T | TAB | Tableau à saisir |
| T1 | TAB | Tableau des pairs |
| T2 | TAB | Tableau des impairs |
| N, N1, N2 | Entier | Tailles |
| Saisir, Extraire, Afficher | Procédure | — |
Programme Pascal :
program Ex5parite;
uses wincrt;
type tab = array[1..10] of integer;
var t, t1, t2 : tab;
n, n1, n2 : integer;
procedure saisir(var t : tab; var n : integer);
var i : integer;
begin
writeln('donner la taille du tableau');
readln(n);
for i := 1 to n do
repeat
writeln('Donner l''élément n°', i);
readln(t[i]);
until t[i] > 0;
end;
procedure extraire(t : tab; n : integer;
var t1 : tab; var j : integer;
var t2 : tab; var k : integer);
var i : integer;
begin
j := 0; k := 0;
for i := 1 to n do
if t[i] mod 2 = 0 then begin
j := j + 1;
t1[j] := t[i];
end
else begin
k := k + 1;
t2[k] := t[i];
end;
end;
procedure afficher(a : tab; b : integer);
var i : integer;
begin
for i := 1 to b do
writeln('l''élément n°', i, ' est : ', a[i]);
end;
begin
saisir(t, n);
extraire(t, n, t1, n1, t2, n2);
writeln('Le tableau des pairs : ');
afficher(t1, n1);
writeln('le tableau des impairs : ');
afficher(t2, n2);
end.
Exercice 6 — Combinaisons C(n, p)
Écrire un programme qui permet de saisir deux entiers n et p (avec 1 ≤ p ≤ n), puis de calculer et afficher le nombre de combinaisons de p éléments parmi n : C(n, p).
Sachant que : C(n, p) = n! / ( p! × (n − p)! )
Voir le corrigé
Modules :
- procédure
Saisir(n, p) - fonction
Calculer(n, p) - fonction
fact(a): factorielle dea
Analyse du programme principal :
NOM : Combinaison
Résultat = Ecrire("La CNP est", CNP)
CNP ← FN Calculer(n, p)
(n, p) = Proc Saisir(n, p)
FIN Combinaison
Algorithme de la fonction Calculer :
0) DEF FN Calculer(n, p : entier) : entier
1) C ← FN Fact(n) DIV ( FN Fact(p) * FN Fact(n - p) )
2) Calculer ← C
3) FIN Calculer
Algorithme de la fonction Fact :
0) DEF FN Fact(a : entier) : entier
1) [f ← 1] Pour i de 2 à a faire
f ← f * i
Fin Pour
2) Fact ← f
3) FIN Fact
Programme Pascal :
Program combinaison;
uses wincrt;
var n, p, cnp : integer;
procedure saisir(var n, p : integer);
begin
write('n= '); readln(n);
repeat
write('p= '); readln(p);
until (p in [1..n]);
end;
function fact(a : integer) : word;
var i : integer; f : word;
begin
f := 1;
for i := 2 to a do f := f * i;
fact := f;
end;
function calculer(n, p : integer) : integer;
begin
calculer := fact(n) div (fact(n - p) * fact(p));
end;
begin
saisir(n, p);
cnp := calculer(n, p);
write('La CNP est ', cnp);
end.
Exercice 7 — Approximation de exp(x)
Écrire un programme qui permet de saisir un réel x entre 0 et 1, puis de calculer et afficher la valeur approchée VA de exp(x) avec la formule :
e^x = 1 + x/1! + x²/2! + x³/3! + x⁴/4! + …
N.B. : Faire le calcul jusqu'à ce que x^i / i! <= 0,001.
Voir le corrigé
program exponentiel;
uses wincrt;
var x, VA : real;
procedure saisir(var x : real);
begin
repeat
writeln('donner un réel entre 0 et 1 :');
readln(x);
until (x >= 0) and (x <= 1);
end;
function fact(a : integer) : word;
var i : integer; f : word;
begin
f := 1;
for i := 2 to a do f := f * i;
fact := f;
end;
function power(x : real; n : integer) : real;
var i : integer; p : real;
begin
p := 1;
for i := 1 to n do p := p * x;
power := p;
end;
function expo(x : real) : real;
var i : integer; s, d, k : real;
begin
s := 1; i := 0;
repeat
i := i + 1;
d := power(x, i) / fact(i);
s := s + d;
until d <= 0.0001; { répéter jusqu'à ce que le terme d soit <= 0.0001 }
expo := s;
end;
begin
saisir(x);
VA := expo(x);
writeln('valeur approchée : ', VA:10:8);
writeln('calcul direct : ', exp(x):10:8);
end.
Exercice 8 — Extraire lettres et chiffres d'une chaîne
Écrire un programme qui permet de saisir une chaîne Ch composée uniquement de chiffres et de lettres, puis d'extraire les lettres dans une chaîne CH1 et les chiffres dans une chaîne CH2.
Voir le corrigé
Analyse du programme principal :
Nom : ex8
Résultat = Ecrire("Lettres=", ch1), Ecrire("Chiffres=", ch2)
(ch1, ch2) = Proc Extraire(ch, ch1, ch2)
ch = Proc Saisir(ch)
Fin ex8
Algorithme de la fonction Verif :
0) DEF FN Verif(ch : chaîne) : booléen
1) [ok ← vrai, i ← 0] Répéter
i ← i + 1
Si Non(ch[i] dans ["0".."9", "a".."z", "A".."Z"])
alors ok ← faux
FinSi
Jusqu'à (i = long(ch)) ou (ok = faux)
2) Verif ← ok
3) Fin Verif
Algorithme de la procédure Extraire :
0) DEF PROC Extraire(ch : chaîne, Var lettres, chiffres : chaîne)
1) [lettres ← "", chiffres ← ""] Pour i de 1 à long(ch) faire
Si ch[i] dans ["0".."9"]
alors chiffres ← chiffres + ch[i]
sinon lettres ← lettres + ch[i]
FinSi
FinPour
2) Fin Extraire
Traduction Pascal :
program ex8;
uses wincrt;
var ch, ch1, ch2 : string;
function verif(ch : string) : boolean;
var i : integer; ok : boolean;
begin
i := 0; ok := true;
repeat
i := i + 1;
if NOT(ch[i] in ['0'..'9', 'a'..'z', 'A'..'Z']) then
ok := false;
until (i = length(ch)) or (ok = false);
verif := ok;
end;
procedure saisir(var ch : string);
begin
repeat
write('ch='); readln(ch);
until verif(ch); { ou : until verif(ch) = true; }
end;
procedure extraire(ch : string; var lettres, chiffres : string);
var i : integer;
begin
lettres := ''; chiffres := '';
for i := 1 to length(ch) do
if ch[i] in ['0'..'9'] then chiffres := chiffres + ch[i]
else lettres := lettres + ch[i];
end;
begin
saisir(ch);
extraire(ch, ch1, ch2);
writeln('lettres=', ch1);
writeln('chiffres=', ch2);
end.
Exercice 9 — Palindrome
Écrire un programme qui inverse une chaîne de caractères de longueur inférieure à 10 caractères, puis indique si c'est un palindrome (s'écrivant de la même façon de gauche à droite et de droite à gauche).
Exemples : radar, elle, …
Voir le corrigé
Analyse du programme principal :
Nom : palindrome
Résultat = Si ch = ch1 alors Ecrire("Palindrome")
Sinon Ecrire("Non palindrome")
Finsi
ch1 ← FN Inverse(ch)
PROC Saisir(ch)
Fin Palindrome
Algorithme de la fonction Inverse :
0) DEF FN Inverse(ch : chaîne) : Chaîne
1) [ch2 ← ""] Pour i de long(ch) à 1 (pas = -1) faire
ch2 ← ch2 + ch[i]
FinPour
2) Inverse ← ch2
3) Fin Inverse
Traduction Pascal :
program palindrome;
uses wincrt;
var ch, ch1 : string;
procedure saisir(var ch : string);
begin
repeat
writeln('Donner un mot ');
readln(ch);
until length(ch) < 10;
end;
function inverse(ch : string) : string;
var ch2 : string;
i : integer;
begin
ch2 := '';
for i := length(ch) downto 1 do
ch2 := ch2 + ch[i];
inverse := ch2;
end;
begin
saisir(ch);
ch1 := inverse(ch);
if ch = ch1 then writeln('Palindrome')
else writeln('non palindrome');
end.
Exercice 10 — Supprimer les caractères répétés
Écrire un programme permettant d'enlever les caractères qui se répètent dans une chaîne ch.
Exemples :
"sciences"→"scien""programmation"→"progamtin"
Voir le corrigé
program car_double;
uses wincrt;
var ch : string;
{ supp_car : supprime toutes les occurrences d'un caractère d'indice i
dans la sous-chaîne située après l'indice i }
function supp_car(ch : string; i : integer) : string;
var c : char; ch1, ch2 : string;
begin
c := ch[i];
ch1 := copy(ch, 1, i);
ch2 := copy(ch, i + 1, length(ch) - i);
repeat
delete(ch2, pos(c, ch2), 1);
until pos(c, ch2) = 0;
supp_car := ch1 + ch2;
end;
{ sup_double : supprime toutes les occurrences de tous les caractères de ch }
function sup_double(ch : string) : string;
var i : integer; ch3 : string;
begin
ch3 := ch;
i := 0;
repeat
i := i + 1;
ch3 := supp_car(ch3, i);
until (i = length(ch3));
sup_double := ch3;
end;
begin
writeln('Donner une chaine '); readln(ch);
writeln(sup_double(ch));
end.
Exercice 11 — Occurrences des lettres d'un mot dans un texte
Écrire un programme qui demande à l'utilisateur un texte et un mot, puis affiche, pour chaque lettre du mot, le nombre d'occurrences de cette lettre dans le texte de départ.
Voir le corrigé
Modules :
- procédure
Saisir(texte, mot) - procédure
Afficher(texte, mot) - fonction
Verif(mot, indice): vérifie qu'on n'a pas déjà traité cette lettre - fonction
Occurrence(c, texte): compte les occurrences
Algorithme de la procédure Afficher :
0) DEF PROC Afficher(texte, mot : chaîne)
1) Pour i de 1 à long(mot) faire
Si Verif(mot, i) alors
Ecrire("Lettre= ", mot[i])
nb ← Occurrence(mot[i], texte)
Ecrire(nb, " fois")
FinSi
FinPour
2) Fin Afficher
Algorithme de la fonction Verif :
0) DEF FN Verif(mot : chaîne, indice : entier) : booléen
1) mot2 ← sous_chaine(mot, 1, indice - 1)
2) Si pos(mot[indice], mot2) = 0 alors Verif ← vrai
Sinon Verif ← faux
FinSi
3) Fin Verif
Algorithme de la fonction Occurrence :
0) DEF FN Occurrence(c : caractère, texte : chaîne) : entier
1) [nb ← 0] Pour j de 1 à long(texte) faire
Si texte[j] = c alors nb ← nb + 1 FinSi
FinPour
2) Occurrence ← nb
3) Fin Occurrence
Programme Pascal :
program nblettres;
uses wincrt;
var texte, mot : string;
procedure saisir(var texte, mot : string);
begin
writeln('Donner un texte'); readln(texte);
writeln('Donner un mot'); readln(mot);
end;
function verif(mot : string; indice : integer) : boolean;
var mot2 : string;
begin
mot2 := copy(mot, 1, indice - 1);
if pos(mot[indice], mot2) = 0 then verif := true
else verif := false;
end;
function occurrence(c : char; texte : string) : integer;
var nb, j : integer;
begin
nb := 0;
for j := 1 to length(texte) do
if texte[j] = c then nb := nb + 1;
occurrence := nb;
end;
procedure afficher(texte, mot : string);
var nb, i : integer;
begin
for i := 1 to length(mot) do
if verif(mot, i) then begin
writeln('Lettre= ', mot[i]);
nb := occurrence(mot[i], texte);
writeln(nb, ' fois');
end;
end;
begin
saisir(texte, mot);
afficher(texte, mot);
end.
Quiz : sous-programmes (procédures et fonctions)
Vérifiez votre compréhension de l'analyse modulaire, des paramètres et de la portée.
Quiz (5 questions)
Quelle est la **différence essentielle** entre une **procédure** et une **fonction** ?
Le passage par **variable** (`@` ou `var`) permet :
Un **objet local** d'une fonction est :
Pourquoi est-il **utile** de décomposer un programme en sous-programmes ?
Considérez cette fonction : ``` DEF FN cube (x : entier) : entier DEBUT cube ← x * x * x FIN ``` Appelée par `y ← FN cube(3) + 2`, que vaut `y` ?