En C, il existe deux méthodes pour passer des variables en paramètre dans une fonction :
C'est la technique "classique" présentée dans le cours 8.1 sur les fonctions. Avec cette approche, la variable transmise est copiée dans la variable locale à la fonctions. Considérons la fonction suivante :
void fct(int arg) {
// Affiche l'adresse de l'argument du pointeur
printf ("Adresse de arg = %p\n", &arg);
}
// Déclare une variable var et affiche son adresse
int var=28;
printf ("Adresse de var = %p\n", &var);
// Appel de la fonction
fct(var);
Lorsque l'on exécute ce programme, on s'aperçoit que la variable var
n'a pas
la même adresse que la variable arg
, locale à la fonction. Il y a donc deux
variables distinctes à deux adresses différentes. Leur seul lien est au moment
de l'appel de la fonction : la valeur de var
est copiée dans arg
.
C'est la raison pour laquelle on parle de passage par valeur. La fonction fct()
ne
peut pas modifier la variable var
.
Aussi appelée passage par référence, cette seconde approche consiste à passer l'adresse de la variable (la référence). Ce faisant, la fonction peut modifier le contenu de la variable, même si elle est locale à une autre fonction.
Considérons les deux fonctions suivantes :
void valeur(int arg) { arg++; }
void variable(int *arg) { (*arg)++; }
Analysons maintenant le code suivant :
int var1=5,var2=5;
// Passage par valeur
valeur(var1);
// Affiche 5 : var1 n'est pas modifié par la fonction
printf ("valeur => var1 = %d\n", var1);
// Passage par variable
variable(&var2);
// Affiche 6 : var2 est modifié par la fonction
printf ("variable => var2 = %d\n", var2);
Lors d'un passage par valeur, la fonction valeur()
ne peut pas modifier le contenu
de la variable transmise (var1
). En revanche, lors d'un passage par variable, la
fonction variable()
peut modifier le contenu de la variable transmise (var2
) :
Comme c'est l'adresse qui est transmise à la fonction, celle-ci peut modifier le contenu de la variable.
valeur => var1 = 5 variable => var2 = 6
Cette technique est utilisée, par exemple, pour contrer la limite du nombre de paramètres
qui peuvent être retournés par une fonction avec return
(c'est-à-dire 1). C'est ce
mécanisme qui est utilisé dans la fonction scanf()
pour que la variable puisse être
modifiée par la fonction.
scanf("%d", &val);
^
Passage par variable
Écrire une fonction permute()
qui inverse le contenu de deux variables :
// Permutte le contenu de a et b
void permute(int *a, int *b);
Voici l'affichage escompté :
Avant : x=7 y=8 Après : x=8 y=7
Écrire une fonction percent()
qui reçoit en paramètre val
un flottant par variable.
val
est supérieur à 100, 100 est affecté à la variable pointée par arg
, la fonction retourne 1 ;val
est inférieur à 0, 0 est affecté à la variable pointée par val
, la fonction retourne -1 ;Après l'appel de la fonction, la variable passée en paramètre doit forcement être comprise entre 0 et 100. Voici quelques exemples escompté :
Entrez un pourcentage : 12.5 12.50% est valide
Entrez un pourcentage : 156.78 C'est trop grand, j'ai remplacé par 100.00%
La fonction main()
accepte deux paramètres :
int main(int argc, char *argv[])
Sous linux, lorsque l'on tape la commande de listage des fichiers ln -a -s
dans
un terminal, on passe les arguments -a
et -s
à une fonction main()
qui a été
programmée en C.
> ls -a -l total 20 drwxr-xr-x 1 runner runner 20 Oct 30 16:27 . drwxr-xr-x 1 runner runner 4096 Oct 30 16:23 .. -rwxr-xr-x 1 runner runner 8392 Oct 30 16:27 main -rw-r--r-- 1 runner runner 515 Oct 30 16:27 main.c
Écrire un programme qui affiche le nombre et le contenu des arguments de la fonction
main()
:
> ./main 1 arguments détectés argv[0] = ./main
> ./main -f test.txt 3 arguments détectés argv[0] = ./main argv[1] = -f argv[2] = test.txt
Écrire une fonction qui calcule les racines d’un polynôme du second degré et qui en renvoie le discriminant :
double polynome (double a, double b, double c, double * r1, double * r2);
Écrire un programme principal qui demande à l’utilisateur de saisir les coefficients du polynôme avant d’en afficher les racines :
Entrez le coefficient a : 2.5 Entrez le coefficient b : 4.6 Entrez le coefficient c : 18.7 -> Racines complexes
Entrez le coefficient a : 1 Entrez le coefficient b : 4 Entrez le coefficient c : 4 -> Deux solutions identiques : x1 = x2 = -2.00
Entrez le coefficient a : 1.4 Entrez le coefficient b : 18.5 Entrez le coefficient c : 2 -> Deux solutions distinctes : x1=-0.11 et x2=-13.11
Cette function accepte quels types de passage de paramètre ?
void fct(int v);
Cette function accepte quels types de passage de paramètre ?
void fct(int *v);
D'un point de vue purement syntaxique, quels types de variable peut-on passer à la fonction suivante ?
void majuscule(char *arg);
Qu'affiche le code suivant ?
void addTwo(int i) { i=i+2; }
int main(void) {
int var=5;
addTwo(var);
printf ("var = %d", var);
}
Qu'affiche le code suivant ?
void addTwo(int *i) { *i=*i+2; }
int main(void) {
int var=5;
addTwo(&var);
printf ("var = %d", var);
}