Corrigé 3
Prérequis
|
1. |
a., b. et d. Un sous-programme contient un nom, un bloc d’instructions et éventuellement des variables locales. |
|
2. |
a. et b. Un sous-programme peut être appelé depuis le programme principal ou depuis un autre sous-programme. |
|
3. |
Une fonction renvoie un résultat, elle est appelée dans une expression. Une procédure ne renvoie pas de résultat, son invocation se fait par une instruction d’appel. |
|
4. |
La valeur de retour d’une fonction est obtenue par l’expression qui suit l’instruction Retourne en langage algorithmique et qui suit l’instruction return en Java et Python. Le type de l’expression doit être compatible avec le type de la fonction. |
Corrigé 3.1 : La bannière de bienvenue
La procédure destinée à afficher la bannière s’appelle ci-dessous afficheBannière. Son contenu est très simple. Elle est appelée dans l’algorithme principal par son nom.
PROGRAMME Bienvenue
PROCÉDURE afficheBannière()
DÉBUT
Écrire "*********************************************"
Écrire "** **"
Écrire "** BIENVENUE **"
Écrire "** **"
Écrire "*********************************************"
FINPROC
DÉBUT
afficheBannière()
// suite de l'algorithme
FIN
En Java, c’est tout aussi simple. Notez le mot clé static devant la déclaration de la procédure.
public class Bienvenue {
public static void afficheBanniere()...Corrigé 3.2 : Initialisation d’une variable tableau
Le but de l’exercice est d’écrire une procédure qui remplit le tableau utilisé dans l’exercice 2.3 avec des nombres aléatoires compris entre 1 et 10. Cette procédure se trouve ci-dessous sous le nom de remplitTableau. Dans cette procédure, un accès à la variable globale tableau est réalisé, cette variable ayant bien été déclarée avant la procédure.
PROGRAMME RechercheValeur
CONST
taille : entier = 10
VAR
i, valeur : entier
tableau : tableau[0..taille-1] d'entiers
PROCEDURE remplitTableau()
VAR
i : entier
DÉBUTPour i De 0 à taille-1 Faire
tableau[i] <- nombreAléatoire(l,10)
FinPour
FINPROC
DÉBUT
// remplissage du tableau
remplitTableau()
// affichage du tableau
Pour i De 0 à taille-1 Faire
Écrire tableau[i]
FinPour
// lire la valeur à rechercher
...Corrigé 3.3 : Affichage d’un tableau
Une nouvelle procédure est créée et invoquée dans notre programme de recherche d’une valeur dans un tableau. Il s’agit de la procédure afficheTableau qui prend comme paramètre modeUneLigne (Java) / mode_une_ligne (Python) qui est de type booléen. Si celui-ci est vrai, alors l’affichage se fait sans saut de ligne.
Cette procédure est appelée dans le programme principal qui demande d’abord à l’utilisateur le mode d’affichage qu’il souhaite.
import java.util.Scanner;
public class RechercheValeurTableau2 {
// déclaration de la constante taille
final static int taille = 10;
// déclaration et création du tableau
static int[] tableau = new int[taille];
public static void remplitTableau() {
int i;
for (i = 0; i < taille; i++)
tableau[i] = (int) (Math.random() * 10) + 1;
}
public static void afficheTableau(boolean modeUneLigne) {
int i;
...Corrigé 3.4 : Fonctions de conversion de degrés en radians et vice versa
La fonction radianVersDegré s’écrit comme suit. Il faut remarquer qu’elle introduit le type du résultat et qu’elle utilise une constante, à savoir PI. L’instruction Retourne permet de spécifier la valeur du résultat.
FONCTION radianVersDegré (angle : réel) : réel
CONST
PI : réel = 3.1415926
DÉBUT
Retourne angle / PI * 180;
FINFONC
La fonction degréVersRadian est écrite de façon tout à fait similaire.
FONCTION degréVersRadian (angle : réel) : réel
CONST
PI : réel = 3.1415926
DÉBUT
Retourne angle / 180 * PI;
FINFONC
En Java, le type du résultat d’une fonction se trouve avant son nom. Il remplace void utilisé pour spécifier une procédure. L’instruction return permet de spécifier la valeur de retour.
Une fonction est invoquée dans une expression, comme ici où radianVersDegre se trouve dans l’expression qui détermine la valeur du paramètre de println.
import java.util.Scanner;
public class ConversionRadianDegreTest {
public static double radianVersDegre(double...Corrigé 3.5 : Fonction de génération d’un nombre entier aléatoire entre une borne inférieure et une borne supérieure
Le but de l’exercice est d’écrire la fonction genereNombreAleatoire qui prend deux paramètres entiers correspondant aux bornes et renvoie un nombre aléatoire entier compris entre celles-ci. Cela aboutit au code suivant en Java.
import java.util.Scanner;
public class GenerationAleatoire {
public static int genereNombreAleatoire(int borneInf, int borneSup) {
return (int) ((borneSup - borneInf + 1) *
Math.random()) + borneInf;
}
public static void main(String[] args) {
Scanner reader = new Scanner(System.in);
int borneInf, borneSup;
int nombreAleatoire;
System.out.print("Entrez la borne inférieure : ");
borneInf = reader.nextInt();
System.out.print("Entrez la borne supérieure : ");
borneSup = reader.nextInt();
nombreAleatoire = genereNombreAleatoire(borneInf, borneSup);
System.out.println("Le nombre aléatoire généré est : "
+ nombreAleatoire);
}
}
Son intégration dans le programme de recherche d’une valeur...
Corrigé 3.6 : Fonction de calcul de la factorielle
La fonction factorielle ainsi que le programme d’appel de cette fonction sont écrits en langage algorithmique à la suite.
Il faut remarquer que la variable globale n et le paramètre n sont deux variables totalement distinctes bien qu’elles possèdent le même nom. Si l’un des deux était renommé différemment, ceci ne changerait rien au sens de l’algorithme.
PROGRAMME CalculFactorielle
VAR
n : entier
FONCTION factorielle (n : entier) : entier
VAR
i, résultat : entier
DÉBUT
Résultat = 1
Pour i De 2 à n Faire
résultat <- résultat* i
FinPour
Retourne résultat
FINFONC
DÉBUT
Lire n
Écrire factorielle(n)
FIN
L’équivalent en Java se trouve à la suite.
import java.util.Scanner;
public class CalculFactorielle {
public static long factorielle(int n) {
long resultat;
resultat = 1;
for (int i = 2; i <= n; i++)
resultat...Corrigé 3.7 : Fonctions min et max de trois nombres réels
Les fonctions min et max qui calculent le minimum et le maximum de trois nombres réels ainsi que l’algorithme principal invoquant ces deux fonctions sont illustrés ci-après.
PROGRAMME MinMax3Nombres
VAR
un, deux, trois : réel
FONCTION min(un, deux, trois : réel) : réel
DÉBUT
Si un < deux Alors
Si un < trois Alors
Retourne un
Sinon
Retourne trois
FinSi
Sinon
Si deux < trois Alors
Retourne deux
Sinon
Retourne trois
FinSi
FinSi
FINFONC
FONCTION max(un, deux, trois : réel) : réel
DÉBUT
Si un > deux Alors
Si un > trois Alors
...Corrigé 3.8 : Fonction calculant la racine carrée d’un nombre réel
La fonction racineCarrée décrite ci-dessous renvoie un booléen dont la valeur est égale à vrai si le calcul est possible, faux sinon. Si le calcul est possible, alors le paramètre résultat contient la valeur de la racine carrée. En effet, il s’agit d’un paramètre en mode sortie, dont la valeur est affectée à la variable utilisée lors de l’appel. Dans l’algorithme principal, l’appel de la fonction se fait avec la variable résultatRacine pour le paramètre en sortie (indiqué par S devant le nom du paramètre).
PROGRAMME CalculRacineCarrée
VAR
X, résultatRacine : réel
FONCTION racineCarrée(x : réel, S résultat : réel) : booléen DÉBUT
Si x >= 0 Alors
résultat <- racine(x)
Retourne VRAI
Sinon
Retourne FAUX
FinSi
FINFONC
DÉBUT
Lire x
Si racineCarrée(x, résultatRacine) Alors
...Corrigé 3.9 : Remplissage d’un tableau d’entiers par des nombres aléatoires
La procédure remplitTableauAléatoire remplit un tableau passé en paramètre (ici en mode sortie) avec des nombres aléatoires compris entre la borne inférieure et la borne supérieure. Ce qu’il est intéressant de noter dans la version algorithmique est l’obligation de passer en paramètre les indices minimum et maximum du tableau.
PROGRAMME RemplissageTableauAléatoire
CONST
taille : entier = 10
VAR
i : entier
tableau : tableau[0..taille-1] d'entiers
PROCEDURE remplitTableauAléatoire (S t : tableau[] d'entiers, minT, maxT, borneinf, borneSup : entier)
VAR
i : entier
DÉBUT
Pour i De minT à maxT Faire
t[i] <- nombreAléatoire(borneinf, borneSup)
FinPour
FINPROC
DÉBUT
remplitTableauAléatoire(tableau, 0, taille-1, 1, 10);
Pour i De 0 à taille-1 Faire
Écrire tableau[i]
FinPour
FIN
Dans la version Java, il ne faut pas passer le minimum et le maximum des indices. En effet, le minimum est toujours zéro et la taille est donnée par la propriété length, ce qui permet de balayer l’ensemble des valeurs du tableau.
Il est intéressant de remarquer que cette fois-ci le mode entrée-sortie du paramètre t est beaucoup plus simple que dans l’exercice précédent. En effet, Java transmet toujours la référence du tableau et non sa valeur. Le mode entrée-sortie est donc le mode par défaut pour un tableau (pour tout objet).
public class RemplissageTableauAleatoire {
public static int genereNombreAleatoire(int borneInf, int
borneSup) {
return (int) ((borneSup - borneInf + 1) *
...Corrigé 3.10 : Division euclidienne
La fonction divisionEuclidienne, qui renvoie un tableau dont le premier élément est le quotient et le second élément le reste, se trouve ci-dessous.
PROGRAMME CalculDivisionEuclidienne
VAR
dividende, diviseur : entier
résultatDivision : tableau[0..1] d'entiers
FONCTION divisionEuclidienne(dividende, diviseur : entier) :
tableau[] d'entiers
VAR
résultat : tableau[0..1] d'entiers
DÉBUT
résultat[0] <- dividende DIV diviseur;
résultat[l] <- dividende % diviseur;
Retourne résultat;
FINFONC
DÉBUT
Lire dividende
Lire diviseur
résultatDivision <- divisionEuclidienne(dividende, diviseur)
Écrire tableau[0]
Écrire tableau[l]
FIN
En Java, le principe est assez proche. Il faut créer un tableau de deux éléments dans la fonction puis le renvoyer.
import java.util.Scanner;
public class CalculDivisionEuclidienne {
public static int[] divisionEuclidienne(int dividende, int diviseur)...Corrigé 3.11 : Recherche d’une valeur dans un tableau d’entiers à deux dimensions
La fonction de recherche dans un tableau à deux dimensions est écrite ci-dessous. Elle prend le tableau et la valeur en paramètres, ainsi que, dans la version algorithmique, les indices minimum et maximum pour chaque dimension du tableau.
La recherche s’effectue à l’aide d’une première boucle sur les lignes du tableau, puis pour chaque ligne une seconde boucle effectue la recherche sur les colonnes.
Si la valeur n’est pas trouvée, les deux indices du résultat sont affectés à minT1-1.
FONCTION rechercheValeurTableauDeuxDim(tab : tableau[][]
d'entiers, valeur, minT1, maxT1, minT2, maxT2 : entier) :
tableau[] d'entiers
VAR
résultat: tableau[0..1] d'entiers
i, j : entier
trouvé : booléen
DÉBUT
i <- minT1
trouvé <- FAUX
Tant Que (i <= maxT1) ET (NON trouvé)
j <- minT2
Tant Que (j <= maxT2) ET (NON trouvé)
Si tab[i][j] = valeur Alors
trouvé <- VRAI
Sinon
j <- j + l
FinSi
FinTantQue
Si NON trouvé
i <- i + 1
FinSi
FinTantQue
Si trouvé Alors
résultat[0] <- i
résultat[1] <- j
...Corrigé 3.12 : Somme de deux matrices carrées d’entiers
Les procédures Java permettant de lire et d’écrire une matrice ainsi que la fonction permettant d’ajouter deux matrices carrées sont présentées à la suite. Le programme principal issu de l’exercice 2.5 est modifié pour intégrer les deux procédures de lecture/écriture ainsi que la fonction d’addition.
import java.util.Scanner;
public class SommeMatricesModulaire {
static Scanner reader = new Scanner(System.in);
public static void lireMatrice(int[][] matrice) {
for (int i = 0; i < matrice.length; i++)
for (int j = 0; j < matrice[i].length; j++) {
System.out.print("Entrez matrice[" + i +
"][" + j + "] : ");
matrice[i][j] = reader.nextInt();
}
}
public static int[][] ajouteMatriceCarree(int[][] matrice1, int[][] matrice2, int taille) {
int[][] resultat = new int[taille][taille];
for (int i = 0; i < taille; i++) {
for (int j = 0; j < taille; j++)
resultat[i][j] = matrice1[i][j] +
matrice2[i][j];
}
return resultat;
}
public static void ecrireMatrice(int[][] matrice) {
for (int i = 0; i < matrice.length; i++)
for (int j = 0; j < matrice[i].length; j++)
System.out.println("matrice[" + i + "][" + j + "] = " + matrice[i][j]);
}
...Corrigé 3.13 : Fusion de deux tableaux triés d’entiers
Le programme de fusion des tableaux dans sa version modulaire est présenté à la suite pour le langage Java. Le programme principal devient beaucoup plus facile à lire et chaque procédure (ou fonction) peut être étudiée facilement, indépendamment des autres.
public class FusionTableauxTriesModulaire {
public static int genereNombreAleatoire(int borneInf, int borneSup) {
return (int) ((borneSup - borneInf + 1) *
Math.random()) + borneInf;
}
public static void remplitTableauAleatoire(int[] t,int borneInf,
int borneSup) {
for (int i = 0; i < t.length; i++)
t[i] = genereNombreAleatoire(borneInf, borneSup);
}
public static void triBulle(int[] t) {
int temp;
boolean permute;
do {
permute = false;
for (int i = 0; i < t.length - 1; i++) {
if (t[i] > t[i + 1]) {
// échange entre t[i] et t[i+1]
temp...