Exercice n°1: Sous-algorithmes "simples"
a) Ecrire un sous-algorithme de calcul du sinus d'un angle donné en degrés.
La fonction développée possède un paramètre d'entête de type réel passé en entrée pour l'angle (en degré). Elle retourne un réel: le sinus
de l'angle.
Une alternative aurait été de développer une fonction sans paramètre retourné, mais avec un paramètre d'entête supplémentaire passé en sortie.
Sinus.lda
{ Calcul du du sinus d'un angle en degres }
constante reel PI <- 3.14159
reel fonction sinus(-> réel angle)
reel sn
sn <- sin(angle*PI/180.0)
retourner sn
fin fonction
Exemple d'exécution
|
b) Ecrire un sous-algorithme de test si un caractère est alphabétique (minuscule ou majuscule).
La fonction développée possède un paramètre d'entête passé en entrée de type caractère pour le caractère à tester. Elle retourne un booléen:
vrai ou faux en fonction du résultat du test.
Une alternative aurait été de développer une fonction sans paramètre retourné, mais avec un paramètre d'entête supplémentaire passé en sortie.
TestCaractereAlphabetique.lda
{ Test si un caractere est alphabetique ou non }
booleen fonction estAlphabetique(-> caractere c)
booleen res
si ( ( c >= 'a' ) et ( c <= 'z' ) ) ou
( ( c >= 'A' ) et ( c <= 'Z' ) ) alors
res <- vrai
sinon
res <- faux
fsi
retourner res
fin fonction
Exemple d'exécution
|
c) Ecrire un sous-algorithme de lecture au clavier d'un nombre entier positif.
Si l'utilisateur frappe une valeur non positive, il devra être sollicité de nouveau jusqu'à ce qu'il tape une valeur admissible.
La fonction développée ne possède pas de paramètre d'entête. Elle retourne un entier: la valeur positive saisie.
Une alternative aurait été de développer une fonction sans paramètre retourné, mais avec un paramètre d'entête passé en sortie.
LectureEntierPositif.lda
{ Lecture au clavier d'une valeur entiere }
{ positive et retour }
entier fonction lectureEntierPositif()
entier valeur
valeur <- Clavier.sasirEntier()
tant que valeur < 0 faire
afficherln("Erreur!!! Veuillez ressaisir)
valeur <- saisir()
fait
retourner valeur
fin fonction
Exemple d'exécution
|
d) Ecrire un sous-algorithme de lecture au clavier d'un nombre réel compris dans un intervalle [min, max].
Si l'utilisateur frappe une valeur en dehors de l'intervalle, il devra être sollicité de nouveau jusqu'à ce qu'il tape une valeur
admissible.
La fonction développée possède deux paramètres d'entête réels passés en entrée: les valeurs min et max. Elle retourne un réel: la valeur saisie
dans l'intervalle [min,max].
Une alternative aurait été de développer une fonction sans paramètre retourné, mais avec un paramètre d'entête supplémentaire passé en sortie.
LectureReelDansIntervalle.lda
{ Lecture au clavier d'une valeur reelle }
{ comprise dans un intervalle et retour }
reel fonction lectureReelDansIntervalle(-> reel min,-> reel max)
reel valeur
valeur <- saisir()
tant que valeur < min ou valeur > max faire
afficherln("Erreur!!! Veuillez ressaisir)
valeur <- saisir()
fait
retourner valeur
fin fonction
Exemple d'exécution
|
e) Ecrire un sous-algorithme d'affichage en hexadécimal d'un nombre entier.
On considérera que le nombre à afficher est compris dans l'intervalle [0,255].
La fonction développée possède un paramètre d'entête de type entier passé en entrée: la valeur à afficher en hexadécimal. Elle retourne aucune
valeur car son but est uniquement de réaliser un affichage.
Une fonction affichageChiffreHexadecimal a été développée pour afficher un chiffre hexadécimal ('0'
à '9' puis 'A' à 'F') suivant sa valeur décimale (0 à 15). Le nombre entier passé en paramètre étant compris entre 0 et 255,
deux chiffres hexadécimaux sont à afficher. La fonction affichageChiffreHexadecimal est appelée
2 fois: une fois pour chacun des 2 chiffres.
AffichageHexadecimal.lda
{ Affichage hexadecimal d'un entier compris entre 0 et 255 }
action affichageHexadecimal(-> entier v)
entier chiffreHaut
entier chiffreBas
chiffreHaut <- v/16
chiffreBas <- v modulo 16
affichageChiffreHexadecimal(chiffreHaut)
affichageChiffreHexadecimal(chiffreBas)
fin action
{ Affichage hexadecimal d'un chiffre }
action affichageChiffreHexadecimal(-> entier chiffre)
dans le cas de chiffre
10 :
afficher('A')
11 :
afficher('B')
12 :
afficher('C')
13 :
afficher('D')
14 :
afficher('E')
15 :
afficher('F')
autre cas :
afficher(chiffre)
fcas
fin action
Exemple d'exécution
|
f) Ecrire un sous-algorithme de calcul de la valeur de sin(a) au voisinage de 0.0 par développement limité.
La formule de calcul est sin(a) = a - a3/3! + a5/5! - a7/7! + a9/9! - ... +/- an/n!
(a en radians)
La fonction développée possède un paramètre d'entête de type réel passé en entrée: la valeur de l'angle (en radians) pour laquelle on calcule
le sinus. Elle retourne une valeur de type réel: la valeur de sinus calculée.
Une alternative aurait été de développer une fonction sans paramètre retourné, mais avec un paramètre d'entête supplémentaire passé en sortie.
Pour optimiser l'exécution, toutes les puissances et toutes les factorielles ne sont pas calculées intégralement. Chaque terme de la suite est
calculé à partir du terme précédent. Le terme 1 est égal à a (a/1). Ensuite chaque terme i est égal au terme i-1 multiplié par a*a et divisé par
i*2-2 et par i*2-1. Le développement limité est obtenu par somme d'un certain nombre de termes.
On notera que, dans l'implantation, plutôt que de numéroter les termes 1, 2, 3, 4, 5, ..., on a préféré les numéroter 1, 3, 5, 7, 9, ...
DeveloppementLimiteSinus.lda
{ Calcul de la valeur de sin(a) au voisinage de 0.0 }
{ Utilisation du developpement limite }
{ Les valeurs a et n sont donnees }
reel fonction sinus(-> reel a,-> entier n)
reel sn
reel terme
entier i
terme <- a
sn <- a
pour i de 3 à n pas 2 faire
terme <- -terme*a*a/(i*(i-1))
sn <- sn + terme
fait
retourner sn
fin fonction
Exemple d'exécution
|
Exercice n°2: Sous-algorithmes avec données agrégées
a) Ecrire un sous-algorithme de calcul du sinus et du cosinus d'un angle donné en degrés.
Première alternative: Développer une fonction avec un paramètre d'entête de type réel passé en entrée pour l'angle (en degré) et deux paramètres
d'entête passés en sortie pour les deux valeurs calculées.
Deuxième alternative: Développer une fonction avec un paramètre d'entête de type réel passé en entrée pour l'angle (en degré) et un paramètre
d'entête passé en sortie agrégeant deux réels (un pour le sinus, un pour le cosinus) (Solution non développée ci-dessous).
Troisième alternative: Développer une fonction avec un paramètre d'entête de type réel passé en entrée pour l'angle (en degré) et une valeur
retournée agrégeant deux réels (un pour le sinus, un pour le cosinus).
CosinusEtSinus.lda
(Solution sans type agrégé)
{ Calcul du cosinus et du sinus d'un angle }
{ donne en degres }
action calculCosinusEtSinus(-> reel angle,reel cosinus ->,reel sinus ->)
reel a
a <- angle*3.1415926535897932/180.0
cosinus <- cos(a)
sinus <- sin(a)
fin action
Exemple d'exécution
|
CosinusEtSinusAvecStructure.lda
(Solution avec type agrégé)
{ Type agrege de stockage du cosinus }
{ et du sinus d'un angle }
structure cosinusEtSinus
reel cosinus <- 1.0
reel sinus <- 0.0
fin structure
{ Calcul du cosinus et du sinus d'un angle }
{ donne en degres }
cosinusEtSinus fonction calculCosinusEtSinus(-> reel angle)
reel a
cosinusEtSinus res
a <- angle*3.1415926535897932/180.0
res.cosinus <- cos(a)
res.sinus <- sin(a)
retourner res
fin fonction
Exemple d'exécution
|
b) Ecrire un sous-algorithme de test de l'inclusion d'un point de coordonnées (x,y) à l'intérieur d'un cercle de rayon
r et de centre (cx,cy).
Première alternative: Développer une fonction avec cinq paramètres d'entête de type réel passés en entrée pour l'abscisse et l'ordonnée
du point testé, le rayon, l'abscisse et l'ordonnée du centre du cercle. Elle retourne une valeur de type booléen: vrai ou faux pour inclusion
ou non inclusion.
Seconde alternativer: Structurer les données et développer une fonction avec deux paramètres d'entête agrégés de type position2D pour le point
testé, et cercle2D pour le cercle. Elle retourne une valeur de type booléen: vrai ou faux pour inclusion ou non inclusion.
TestInclusion.lda
(solution sans type agrégé)
{ Test de l'inclusion d'un point dans un cercle }
{ Les coordonnees du point sont donnees }
{ ainsi que le rayon et les coordonnees }
{ du centre du cercle }
booleen fonction testInclusion(-> reel x,-> reel y,-> reel rayon,-> reel cx,-> reel cy)
booleen inclus
reel distance
distance <- sqrt((x-cx)*(x-cx)+(y-cy)*(y-cy))
si distance < rayon alors
inclus <- vrai
sinon
inclus <- faux
fsi
retourner inclus
fin fonction
Exemple d'exécution
|
TestInclusionAvecStructure.lda
(solution avec types agrégés)
{ Type agrege de stockage d'une position du plan }
structure position2D
reel x <- 0.0
reel y <- 0.0
fin structure
{ Type agrege de stockage d'un cercle du plan }
structure cercle2D
position2D centre
reel rayon <- 1.0
fin structure
{ Test de l'inclusion d'une position du plan }
{ dans un cercle du plan }
booleen fonction testInclusion(-> position2D p,-> cercle2D c)
reel dx
reel dy
reel distance
booleen inclus
dx <- p.x-c.centre.x
dy <- p.y-c.centre.y
distance <- sqrt(dx*dx+dy*dy)
inclus <- (distance <= c.rayon)
retourner inclus
fin fonction
Exemple d'exécution
|
c) Ecrire un sous-algorithme de calcul de la surface d'un rectangle du plan à cotés parallèles aux axes.
Le rectangle est représenté par la position de 2 sommets opposés du rectangle.
Première alternative: Développer une fonction avec quatre paramètres d'entête de type réel passés en entrée pour l'abscisse et l'ordonnée
du premier sommet et l'abscisse et l'ordonnée du second sommet. Elle retourne une valeur de type réel: la surface.
Seconde alternativer: Structurer les données et développer une fonction avec un paramètre d'entête agrégé de type rectangle2D passé en entrée.
Elle retourne une valeur de type réel: la surface.
SurfaceRectangle.lda
(solution sans type agrégé)
{ Calcul de la surface d'un rectangle }
{ Les coordonnees de deux coins opposes }
{ sont donnees }
entier fonction surfaceRectangle(-> reel px1,-> reel py1,-> reel px2,-> reel py2)
reel surface
surface <- abs(px2-px1)*abs(py2-py1)
retourner surface
fin fonction
Exemple d'exécution
|
SurfaceRectangleAvecStructure.lda
(solution avec types agrégés)
{ Type agrege de stockage d'une position du plan }
structure position2D
reel x <- 0.0
reel y <- 0.0
fin structure
{ Type agrege de stockage d'un rectangle du plan }
structure rectangle2D
position2D p1
position2D p2
fin structure
{ Calcul de la surface d'un rectangle 2D }
entier fonction surfaceRectangle(-> rectangle2D r)
reel surface
surface <- abs(r.p2.x-r.p1.x)*abs(r.p2.y-r.p1.y)
retourner surface
fin fonction
Exemple d'exécution
|
Exercice n°1fbis: Sous-algorithme à plusieurs niveaux
Reprendre l'exercice 1f en programmant le calcul du développement limité avec utilisation de fonctions pour les calculs de puissance et de factoriel.
DeveloppementLimiteSinusAvecFonctions.lda
{ Calcul de la puissance entiere d'un reel }
{ Les valeurs a reelle et n entiere sont donnees }
reel fonction puissance(-> reel a,-> entier n)
reel res
entier i
res <- a
pour i de 1 à n-1 faire
res <- res*a
fait
retourner res
fin fonction
{ Calcul de n! }
{ La valeur n entiere est donnee }
entier fonction factoriel(-> entier n)
entier fct
entier i
fct <- 1
pour i de 2 à n faire
fct <- fct*i
fait
retourner fct
fin fonction
{ Calcul de la valeur de sin(a) au voisinage de 0.0 }
{ Utilisation du developpement limite }
{ Les valeurs a et n sont donnees }
reel fonction sinus(-> reel a,-> entier n)
reel sn
reel signe
entier i
signe <- -1.0
sn <- a
pour i de 3 à n pas 2 faire
sn <- sn + puissance(a,i)/factoriel(i)
signe <- -signe
fait
retourner sn
fin fonction
Exemple d'exécution
|
Exercice n°3: Sous-algorithmes à plusieurs niveaux et données agrégées
a) Ecrire un sous-algorithme de test si une année est bissextile.
La fonction développée possède un paramètre d'entête de type entier passé en entrée pour l'année testée. Elle retourne un booléen: vrai ou
faux en fonction de la bissextilité de l'année.
TestBissextile.lda
{ Test si une annee est bissextile }
{ version 1 }
booleen fonction estBissextile(-> entier annee)
booleen res
si annee modulo 400 == 0 alors
res <- vrai
sinon
si annee modulo 100 == 0 alors
res <- faux
sinon
si annee modulo 4 == 0 alors
res <- vrai
sinon
res <- faux
fsi
fsi
fsi
retourner res
fin fonction
{ version 2 }
booleen fonction estBissextile(-> entier annee)
booleen res
si ( annee modulo 400 == 0 ) ou
( ( annee modulo 100 <> 0 ) et ( annee modulo 4 == 0 ) ) alors
res <- vrai
sinon
res <- faux
fsi
retourner res
fin fonction
Exemple d'exécution
|
b) Ecrire un sous-algorithme de calcul du nombre de jours d'un mois codé sous la forme d'un nombre.
La fonction développée possède deux paramètres d'entête de type entier passés en entrée pour le mois et l'année testés. Elle retourne un
entier: le nombre de jours du mois.
NombreJoursMois.lda
{ Calcul du nombre de jours d'un mois }
{ Si le numero de mois est invalide, }
{ la fonction retourne -1 }
entier fonction nombreJoursMois(-> entier mois,-> entier annee)
entier res
dans le cas de mois
2 :
si estBissextile(annee) alors
res <- 29
sinon
res <- 28
fsi
4 :
6 :
9 :
11 :
res <- 30
1 :
3 :
5 :
7 :
8 :
10 :
12 :
res <- 31
autre cas :
res <- -1
fcas
retourner res
fin fonction
Exemple d'exécution
|
c) Ecrire un sous-algorithme de calcul de la date du jour suivant immédiatement une date codée sous la forme jour-mois-année
en nombres.
Solution 1: La fonction développée possède un paramètre d'entête passé en entrée de type date. Elle retourne une date: la date correspondant
au jour suivant la date passée en entête.
Solution 2: L'action développée possède deux paramètres d'entête. Le premier est passé en entrée et est de type date. Le second est passé
en sortie et est de type date. Le second paramètre est destiné à recueillir la date calculée
JourSuivant.lda
structure date
entier jour <- 1
entier mois <- 1
entier annee <- 1901
fin structure
{ Calcul de la date suivant une date codee }
{ sous la forme jour mois annee en entier }
{ Version 1 }
date fonction jourSuivant(-> date d)
date dt
dt.annee <- d.annee
dt.mois <- d.mois
dt.jour <- d.jour+1
si dt.jour > nombreJoursMois(d.mois,d.annee) alors
dt.jour <- 1
dt.mois <- dt.mois+1
si dt.mois > 12 alors
dt.mois <- 1
dt.annee <- dt.annee+1
fsi
fsi
retourner dt
fin fonction
{ Version 2 }
action jourSuivant(-> date d,date dt ->)
dt.annee <- d.annee
dt.mois <- d.mois
dt.jour <- d.jour+1
si dt.jour > nombreJoursMois(d.mois,d.annee) alors
dt.jour <- 1
dt.mois <- dt.mois+1
si dt.mois > 12 alors
dt.mois <- 1
dt.annee <- dt.annee+1
fsi
fsi
fin action
Exemple d'exécution
|
d) Ecrire un sous-algorithme de modification d'une date codée sous la forme jour-mois-année en nombres pour l'incrémenter de
un jour.
jourDApres.lda
structure date
entier jour <- 1
entier mois <- 1
entier annee <- 1901
fin structure
{ Modification d'une date codee sous forme }
{ jour mois annee en entier pour passer }
{ au jour d'apres }
action jourDApres(-> date d ->)
d.jour <- d.jour+1
si d.jour > nombreJoursMois(d.mois,d.annee) alors
d.jour <- 1
d.mois <- d.mois+1
si d.mois > 12 alors
d.mois <- 1
d.annee <- d.annee+1
fsi
fsi
fin action
Exemple d'exécution
|
|