Adresse, valeur...
Rappel pour un nombre
Dans l'exécution du code ci-dessous, vous devez normalement vous attendre à ce que le nombre a ne soit pas modifié après l'exécution de la fonction :
def f(a) :
print('Entrée dans la fonction f.')
a = a+3
print('Valeur de a dans f : ', a)
print('Sortie de f.')
a = 5
print('Valeur de a avant appel de f : ', a)
f(a)
print('Retour au programme principal.')
print('Valeur de a : ', a)
donne :
Valeur de a avant appel de f : 5 Entrée dans la fonction f. Valeur de a dans f : 8 Sortie de f. Retour au programme principal. Valeur de a : 5
Effectuons maintenant une démarche analogue avec une liste en paramètre de f plutôt qu'un nombre.
def f(a) :
print('Entrée dans la fonction f.')
a.append(3)
print('Valeur de a dans f : ', a)
print('Sortie de f.')
a = [2,0,6]
print('Valeur de a avant appel de f : ', a)
f(a)
print('Retour au programme principal.')
print('Valeur de a : ', a)
On obtient :
Valeur de a avant appel de f : [2, 0, 6] Entrée dans la fonction f. Valeur de a dans f : [2, 0, 6, 3] Sortie de f. Retour au programme principal. Valeur de a : [2, 0, 6, 3]
La liste a donc été modifiée en sortie de fonction !
Pour mieux comprendre ce qu'il se passe, regardons l'effet de la variante ci-dessous :
def f(a) :
print('Entrée dans la fonction f.')
a = a+[3]
print('Valeur de a dans f : ', a)
print('Sortie de f.')
a = [2,0,6]
print('Valeur de a avant appel de f : ', a)
f(a)
print('Retour au programme principal.')
print('Valeur de a : ', a)
Résultat de l'exécution de ce code :
Valeur de a avant appel de f : [2, 0, 6] Entrée dans la fonction f. Valeur de a dans f : [2, 0, 6, 3] Sortie de f. Retour au programme principal. Valeur de a : [2, 0, 6]
Cette fois la liste n'est pas modifiée par la fonction.
Pour bien saisir ce qu'il se passe, n'hésitez pas à relire cette page.
Lors de l'appel de la fonction f(a), une copie de a est réalisée. Mais cette copie est réalisée par alocalfonction= aglobal et non par alocalfonction= deepcopy(aglobal).
C'est donc en fait l'adresse de la liste qui est copiée et le a local de la fonction désigne donc la liste globale.
Lorsqu'on utilise, dans la fonction, une méthode qui agit sur la liste elle-même, on modifie donc également la liste de la partie
principale puisqu'il s'agit du même objet.
Par contre, lorsqu'on utilise une affectation a = a+[3]
, une nouvelle liste a est créée, de façon locale à f, et cette nouvelle liste
est donc oubliée en sortie de f.
Dans votre projet pour la fin d'année, vous aurez très certainement à utiliser des listes. N'hésitez pas alors à relire et méditer les exemples ci-dessus en cas de comportement inattendu. Le principe n'est pas très compliqué mais demande à être manipulé pour être bien saisi.