Licence MPI, Semestre 1, Introduction `a l`informatique (Info 111

Transcription

Licence MPI, Semestre 1, Introduction `a l`informatique (Info 111
Licence MPI, Semestre 1, Introduction à l’informatique (Info 111)
Année 2015–2016
TD 5 : Fonctions et tableaux
Exercice 1.
On considère le programme suivant :
#include <i o s t r e a m >
#include <v e c t o r >
using namespace s t d ;
int mystere ( v e c t o r <int> t ) {
int m = t [ 0 ] ;
f o r ( int i = 1 ; i < t . s i z e ( ) ; i++ ) {
if ( m < t [ i ] )
m = t[i];
}
return m ;
}
int main ( ) {
v e c t o r <int> t = { 5 , −1, 3 , 7 , −4, 8 , 4 } ;
c o u t << mystere ( t ) << e n d l ;
return 0 ;
}
(1) Exécuter pas à pas ce programme, que fait-il ? Que fait la fonction mystere ?
Correction Ce programme affiche 8. La fonction mystère calcule le maximum du
tableau.
(2) Modifier le programme pour qu’il affiche le minimum et le maximum d’un tableau.
Correction
#include <i o s t r e a m >
#include <v e c t o r >
using namespace s t d ;
/∗ ∗ Renvoie l ’ é l é ment l e p l u s grand du t a b l e a u ∗ ∗/
int max( v e c t o r <int> t ) {
int m = t [ 0 ] ;
f o r ( int i = 1 ; i < t . s i z e ( ) ; i++ ) {
if ( t [ i ] > m )
m = t[i];
}
return m ;
}
/∗ ∗ Renvoie l ’ é l é ment l e p l u s p e t i t du t a b l e a u ∗ ∗/
int min ( v e c t o r <int> t ) {
int m = t [ 0 ] ;
f o r ( int i = 1 ; i < t . s i z e ( ) ; i++ ) {
if ( t [ i ] < m )
m = t[i];
}
return m ;
1
2
TD 5 : FONCTIONS ET TABLEAUX
}
int main ( ) {
v e c t o r <int> tab = { 5 , −1, 3 , 7 , −4, 8 , 4 } ;
c o u t << ”Le max e s t ”<< max( tab ) <<e n d l ;
c o u t << ”Le min e s t ”<< min ( tab ) <<e n d l ;
return 0 ;
}
Exercice 2.
Quelques fonctions sur les tableaux :
(1) Spécifier et écrire une fonction qui affiche les éléments d’un tableau.
Correction
/∗ ∗ A f f i c h e un t a b l e a u
∗ @param t a b un t a b l e a u d ’ e n t i e r s
∗ ∗/
void a f f i c h e T a b l e a u ( v e c t o r <int> tab ) {
f o r ( int i =0 ; i <tab . s i z e ( ) ; i ++) {
cout<<tab [ i ]<< ’ \ t ’ ;
}
cout<<e n d l ;
}
(2) Spécifier et écrire une fonction qui teste si deux tableaux sont égaux.
Correction
/∗ ∗ T e s t e s i deux t a b l e a u x s o n t é gaux
( t a i l l e s é g a l e s , é l é ments de même i n d i c e é gaux )
∗ @param t a b 1 l e p r e m i e r t a b l e a u d ’ e n t i e r s
∗ @param t a b 2 l e d e u x i ème t a b l e a u d ’ e n t i e r s
∗ @return v r a i s i l e s deux t a b l e a u x s o n t é gaux , f a u x s i n o n
∗ ∗/
bool t e s t E g a u x ( v e c t o r <int> tab1 , v e c t o r <int> tab2 ) {
int t a i l l e = tab1 . s i z e ( ) ;
i f ( tab2 . s i z e ( ) != t a i l l e ) {
return f a l s e ;
}
else {
f o r ( int i =0 ; i < t a i l l e ; i ++) {
i f ( tab1 [ i ] != tab2 [ i ] ) {
return f a l s e ;
}
}
return true ;
}
}
(3) Spécifier et écrire une fonction qui compte le nombre d’éléments plus grands que 10
dans un tableau d’entiers.
Correction
/∗ ∗ Compte l e nombre d ’ é l é ments p l u s g r a n d s que 10 dans l e t a b l e a u
∗ @param t a b un t a b l e a u d ’ e n t i e r
∗ @return nombre d ’ é l é ments p l u s grand que 10
∗/
TD 5 : FONCTIONS ET TABLEAUX
3
int plusGrandQueDix ( v e c t o r <int> tab ) {
int r e s = 0 ;
f o r ( int i =0 ; i <tab . s i z e ( ) ; i ++) {
i f ( tab [ i ] > 1 0 )
res = res + 1 ;
}
return r e s ;
}
(4) Spécifier et écrire une fonction qui renvoie vrai si un tableau d’entiers est trié dans
l’ordre croissant, et faux sinon.
Correction
/∗ ∗ T e s t e s i un t a b l e a u e s t t r i é en o r d r e c r o i s s a n t
∗ @param t a b un t a b l e a u d ’ e n t i e r
∗ @return t r u e s i l e t a b l e a u e s t t r i é en o r d r e c r o i s s a n t , f a l s e s i n o n
∗/
bool e s t T r i e ( v e c t o r <int> tab ) {
f o r ( int i =0 ; i <tab . s i z e () −1 ; i ++) {
i f ( tab [ i ] > tab [ i +1])
return f a l s e ;
}
return true ;
}
Exercice 3.
On rappelle que la suite de Fibonacci est définie récursivement par la relation : Un =
Un−1 + Un−2 . Cette définition doit être complétée par une condition d’initialisation, en
l’occurrence : U1 = U2 = 1. Introduite par Léonard de Pise (surnommé Fibonacci), cette
suite décrit l’évolution d’un modèle simple de population de lapins. Les premiers termes
sont donnés par : 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377, 610, ... Voir aussi
http://oeis.org/A000045.
4
TD 5 : FONCTIONS ET TABLEAUX
L’objectif est d’implanter la fonction dont la documentation et les tests sont donnés
ci-dessous :
/∗ ∗ S u i t e de F i b o n a c c i
∗ @param n un e n t i e r s t r i c t e m e n t p o s i t i f
∗ @return l e n−i ème terme de l a s u i t e de F i b o n a c c i
∗ ∗/
int f i b o n a c c i ( int n ) {
// À f a i r e : É c r i r e l e code i c i !
}
void f i b o n a c c i T e s t ( ) {
ASSERT( f i b o n a c c i ( 1 )
ASSERT( f i b o n a c c i ( 2 )
ASSERT( f i b o n a c c i ( 3 )
ASSERT( f i b o n a c c i ( 4 )
ASSERT( f i b o n a c c i ( 5 )
ASSERT( f i b o n a c c i ( 6 )
}
==
==
==
==
==
==
1
1
2
4
5
8
);
);
);
);
);
);
(1) Vérifier que les tests sont cohérents avec la documentation. Corriger si nécessaire.
Correction
ASSERT( f i b o n a c c i T a b l e a u ( 4 ) == 3 ) ;
(2) Première implantation : en utilisant une boucle for et un tableau de taille n pour
stocker tous les éléments de la suite U1 , . . . , Un .
Correction
int f i b o n a c c i T a b l e a u ( int n ) {
i f ( n == 1 or n == 2 ) {
return 1 ;
} else {
v e c t o r <int> u ( n ) ;
u[0] = 1 ;
u[1] = 1 ;
f o r ( int i = 2 ; i < n ; i ++) {
u [ i ] = u [ i −1] + u [ i −2] ;
}
return u [ n −1] ;
}
}
(3) Deuxième implantation : en utilisant une boucle for et trois variables dont deux
qui, au début de chaque tour de boucle, contiennent les valeurs de Uk−1 et Uk−2 .
Correction
int f i b o n a c c i V a r i a b l e s ( int n ) {
int u1 = 1 ;
int u2 = 1 ;
int tmp = 0 ;
i f ( n == 1 or n == 2 ) {
return 1 ;
} else {
f o r ( int i = 3 ; i <= n ; i ++) {
tmp = u2 ;
u2 = u1 + u2 ;
u1 = tmp ;
TD 5 : FONCTIONS ET TABLEAUX
5
}
return u2 ;
}
}
(4) Troisième implantation : en utilisant une fonction récursive, c’est-à-dire qui s’appelle
elle même.
Correction
int f i b o n a c c i R e c u r s i v e ( int n ) {
i f ( n == 1 or n == 2 ) {
return 1 ;
} else {
return f i b o n a c c i R e c u r s i v e ( n−2) + f i b o n a c c i R e c u r s i v e ( n−1) ;
}
}
(5) Laquelle de ces trois implantations est la plus expressive ?
Correction La fonction récursive : elle correspond à la définition mathématique de
la suite.
(6) ♣ Comparer l’efficacité des trois implantations. Quel phénomène a lieu pour la
fonction récursive ? Comment pourrait-on le corriger ?
Exercice ♣ 4.
(1) Que fait la fonction suivante ?
v e c t o r <int> mystere ( v e c t o r <int> t ) {
int n = t . s i z e ( ) ;
v e c t o r <int> r ( n ) ;
f o r ( int i =0 ; i <n ; i ++)
r [ i ] = t [ n−1− i ] ;
return r ;
}
(2) Un palindrome est un tableau qui peut se lire de la même façon dans les deux sens.
Par exemple le tableau {2, 8, −1, 6, −1, 8, 2} est un palindrome. Écrire une fonction
qui teste si un tableau est un palindrome en utilisant les fonctions déjà vues dans le
TD.
(3) Écrire une fonction palindrome indépendamment des exercices précédents.
(4) Commenter les avantages et inconvénients de chacune.
Correction
bool p a l i n d r o m e ( v e c t o r <int> t ) {
return t e s t E g a u x ( t , m i r r o r ( t ) ) ;
}
bool p a l i n d r o m e I n d e p e n d a n t ( v e c t o r <int> t ) {
int n = t . s i z e ( ) ;
f o r ( int i = 0 ; i < n /2 ; i ++) {
i f ( t [ i ] != t [ n−i −1])
return f a l s e ;
6
TD 5 : FONCTIONS ET TABLEAUX
}
return true ;
}
void p a l i n d r o m e T e s t ( ) {
ASSERT (
palindrome ({
ASSERT (
palindrome ({
ASSERT ( not p a l i n d r o m e ( {
ASSERT ( not p a l i n d r o m e ( {
ASSERT ( not p a l i n d r o m e ( {
}
1 ,2 ,3 ,4 ,5 ,4 ,3 ,2 ,1
1 ,2 ,3 ,4 ,4 ,3 ,2 ,1
1 ,2 ,3 ,4 ,4 ,3 ,2 ,0
1 ,2 ,3 ,4 ,5 ,3 ,3 ,2 ,1
1 ,2 ,3 ,4 ,3 ,3 ,2 ,1
})
})
})
})
})
);
);
);
);
);
int main ( ) {
palindromeTest ( ) ;
return 0 ;
}
La première est plus concise et expressive (proche de la définition mathématique). La
deuxième est plus optimisée.

Documents pareils