Langage C - Pointeurs (Quelques explications) - C - Programmation
Marsh Posté le 10-10-2013 à 12:14:37
J'vais tenter de tout expliquer
Un pointeur est un type de variable qui contient une adresse, et pas une valeur.
La déclaration :
Code :
|
Pour la manipulation :
Code :
|
Il faut penser à un truc :
Comme un pointeur est un type de variable comme un autre, il n'est pas initialisé par défaut, c'est à dire que de déclarer un pointeur comme ceci :
Code :
|
Aura pour effet de lui assigner une valeur "aléatoire" (Considère ça comme ça, c'est pas tout à fait aléatoire mais au final ça revient au même ). Si jamais tu déférence ce pointeur comme ça :
Code :
|
Tu auras environ 60% de chance pour que ton programme plante.
Il faut toujours penser à initialiser un pointeur sur la valeur NULL, c'est un "standard" pour dire qu'un pointeur ne contient pas d'adresse.
Pour ce qui est de l'usage des pointeurs :
- Ça évite la copie en appel de fonction (Quand tu fais passer des grosses structures bien lourde, vaut mieux faire passer par pointer)
- Ça peut aussi permettre de modifier des valeurs d'arguments :
Code :
|
- Ça permet de faire des tableaux dynamiques (mais faut avoir vu malloc / free d'abord).
- C'est utilisé pour les listes chaînés
- Et pas mal d'autre trucs
Marsh Posté le 14-10-2013 à 08:30:22
ludoztw a écrit : Bonjour à tous, |
Bonjour
Tant pis pour l'évaluation, j'arrive trop tard. Toutefois, ce n'est pas pour ça que tu doives laisser tomber.
Donc comme cela a été dit, un pointeur est une variable faite pour contenir une adresse, généralement l'adresse d'une autre variable
Exemple
Code :
|
A quel moment est-ce vraiment utile ?
Généralement dans 2 cas principaux
1) quand une fonction doit modifier une variable qui appartient à une autre fonction
Comme la plage d'adressage de l'ensemble des variables du programme est globale et unique ; et parce qu'une fonction ne reçoit qu'une copie de ce qu'on lui passe, si elle doit modifier une autre variable il faut alors lui passer l'adresse de cette autre variable.
Exemple
Code :
|
2) Quand tu dois faire passer à une autre fonction un élément complexe (une structure, un tableau). Comme là encore la fonction recevra une copie de ce que tu lui passes, il vaut mieux lui passer l'adresse de l'élément (la copie se fera sur une simple adresse de 2 ou 4 octets plutôt que sur l'élément lui-même qui peut avoir plusieurs milliers d'octets)
Exemple
Code :
|
Tous les autres cas où on utilise les adresses ne dérivent que de ces deux cas principaux.
ludoztw a écrit : - Je m'embrouille aussi avec l'utilisation de l'adresse (& ), du *, et de l'utilisation de la simple variable. Si quelqu'un pouvait me réexpliquer brièvement, ce serait for sympathique |
Pas de souci
Là encore ça se divise en 2 cas
1er cas: tu dois utiliser le pointeur (ou plus précisément le contenu de l'adresse). Dans ce cas, il te faut mettre autant d'étoiles que le pointeur en a
Exemple: int ***pt: Adresse de l'adresse de l'adresse d'un entier
Si tu veux obtenir cet entier, il te faut demander ***pt
Exemple: int var=***pt;
2° cas: tu veux remplir un pointeur. Dans ce cas, il te faut juste connaitre la nature de ce que tu as en main pour savoir comment le référencer pour que le pointeur soit correctement rempli
Prenons mon second exemple
Code :
|
La fonction "modif" est sensé recevoir l'adresse d'un entier ; et stocker cette adresse dans la variable "local".
Exemple n° 1: tu as, de ton coté, un entier => int i=100
Si tu veux passer ce "i" à la fonction, comme la fonction doit recevoir une adresse, il te faut lui passer l'adresse de cet entier
Code :
|
Exemple n° 2: tu as maintenant l'adresse d'un entier => int *pt
Puisque pt est déjà une adresse, il te suffit alors de le passer directement à la fonction
Code :
|
Exemple n° 3: tu as un tableau d'entiers => int tab[]={...,...,...}
Puisque la fonction n'est prévue que pour l'adresse d'un entier, et que chaque tab[x] correspond à un entier, il te suffit de passer l'adresse de cet entier (&tab[x]) à la fonction. Toutefois, puisque l'arithmétique des pointeurs dit que &tab[x] équivaut à tab + x, tu peux alors utiliser cette équivalence pour simplifier l'écriture (attention cela n'optimise que l'écriture et en rien le code car dans les deux cas il y a toujours une addition de faite)
Code :
|
Remarque sur l'exemple n° 3: dans le cas où tu travailles souvent sur tab[x], tu sais que chaque appel à tab[x] se soldera par un décalage de x positions à partir de tab (donc une addition) ; tu peux pour optimiser les appels, mémoriser ce décalage dans un pointeur dédié puis utiliser ce pointeur à la place de tab[x]. Ainsi, le décalage (l'addition) ne se fera qu'une fois.
Exemple
Code de base
Code :
|
Code optimisé
Code :
|
Et on peut en plus utiliser les possibilités de la virgule pour le raccourcir de cette façon
Code :
|
Cet exemple pourrait être le 3° cas d'utilisation des pointeurs mais comme c'est facultatif je préfère le laisser comme cas particulier qui dérive du cas n° 2
Marsh Posté le 14-10-2013 à 20:54:16
Bonjour
Je n'avais pas laisser tomber ne t'en fait pas Grâce à toi j'ai mieux compris & eu une note correcte
Merci pour tes suppléments Sve@r
Marsh Posté le 09-10-2013 à 22:45:51
Bonjour à tous,
J'ai demain une évaluation sur les pointeurs en langage C.
J'ai bien bossé mon cours ainsi que mes TP mais tout n'est pas pour autant clair dans ma tête.
Ce chapitre reste toujours vague.Mes questions sont les suivantes :
- A quoi sert réellement un pointeur? Dans quel cas est-il vraiment utile?
- Je m'embrouille aussi avec l'utilisation de l'adresse (& ), du *, et de l'utilisation de la simple variable. Si quelqu'un pouvait me réexpliquer brièvement, ce serait for sympathique
Avant de poster ce message, j'ai biensur rechercher longuement sur internet, mais les explications qui sont données ne font que m'embrouiller.
Merci