IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

 C Discussion :

Passage par adresse ou par valeur ?


Sujet :

C

  1. #1
    Nouveau membre du Club
    Inscrit en
    Janvier 2007
    Messages
    43
    Détails du profil
    Informations forums :
    Inscription : Janvier 2007
    Messages : 43
    Points : 31
    Points
    31
    Par défaut Passage par adresse ou par valeur ?
    Bonjour

    Je suis débutant en C et j'aimerais savoir si le programme ci-dessous utilise le passage par adresse ou par valeur ?? C'est moi qui est écrit ce programme en tatonnant avec les pointeurs. En fait je ne sais jamais s'il faut mettre le * ou pas ??

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
     
    #include <stdio.h>
    #include <stdlib.h>
     
    typedef struct bateau_s{
    	int longueur;
    }bateau;
     
    bateau taille( int n_b , bateau *b )
    {
    	int i;
    	for(i=1;i<=n_b;i++)
    	{
    		(b+i)->longueur = i;
    	}	
     return *b;
    }
     
    int main(void)
    {
    	int i, nbre_bato;
    	bateau *bato; 
     
    	printf("nbre de bato: ");
    	scanf(" %d",&nbre_bato);
     
    	bato = (bateau *)malloc( nbre_bato*sizeof(bateau) );
     
    	*bato = taille( nbre_bato , bato );
     
    	for(i=1;i<=nbre_bato;i++)
    	{
    		printf("bato %d = %d\n",i,(bato+i)->longueur);
    	}	
     
     return 0;
    }
    Merci

  2. #2
    Expert éminent sénior
    Avatar de diogene
    Homme Profil pro
    Enseignant Chercheur
    Inscrit en
    Juin 2005
    Messages
    5 761
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Enseignant Chercheur
    Secteur : Enseignement

    Informations forums :
    Inscription : Juin 2005
    Messages : 5 761
    Points : 13 926
    Points
    13 926
    Par défaut
    1-
    j'aimerais savoir si le programme ci-dessous utilise le passage par adresse ou par valeur ??
    En C, il n'existe que des passages par valeur. Il est pernicieux de parler de passage par adresse lorsqu'on passe l'adresse d'un objet. En fait, on passe la valeur de l'adresse d'un objet, pas l'objet lui-même.
    2-
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    bateau taille( int n_b , bateau *b )
    {
    	int i;
    	for(i=1;i<=n_b;i++)
    	{
    		(b+i)->longueur = i;
    	}	
     return *b;
    Les indices de tableau vont de 0 à (nombre d'éléments -1) et non pas de 1 à (nombre d'éléments )
    3-
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    *bato = taille( nbre_bato , bato );
    bato est déjà l'adresse du début du tableau. La fonction taille peut donc modifier les éléments du tableau indépendamment de la valeur de retour

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    void taille( int n_b , bateau *b )
    {
    	int i;
    	for(i=0;i<n_b;i++)
    		(b+i)->longueur = i;	
    }
    3- Il est inutile (et on considère que c'est plutôt néfaste) de caster le retour de malloc :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    bato = malloc( nbre_bato*sizeof *bato );
    Publication : Concepts en C

    Mon avatar : Glenn Gould

    --------------------------------------------------------------------------
    Une réponse vous a été utile ? Remerciez son auteur en cliquant le pouce vert !

  3. #3
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 518
    Points
    41 518
    Par défaut
    Comme tu as un tableau de structure, tu peux utiliser directement la notation "tableau" :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    void taille( int n_b , bateau *b )
    {
    	int i;
    	for(i=0 ; i<n_b ; i++)
    		b[i].longueur = i;	
    }
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  4. #4
    Nouveau membre du Club
    Inscrit en
    Janvier 2007
    Messages
    43
    Détails du profil
    Informations forums :
    Inscription : Janvier 2007
    Messages : 43
    Points : 31
    Points
    31
    Par défaut
    Merci pour vos réponses diogene et Médinoc

    J'ai maintenant un autre probléme. j'ai séparé mon fichier source en 2 fichiers .c et un .h ainsi qu'un fichier Makefile pour le builder
    Voici mes fichier:

    ex.c
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    #include <stdio.h>
    #include <stdlib.h>
     
    #include "ex.h"
     
    typedef struct bateau_s{
    	int longueur;
    }bateau;
     
    int main(void)
    {
    	int i, nbre_bato;
    	bateau *bato; 
     
    	printf("nbre de bato: ");
    	scanf(" %d",&nbre_bato);
     
    	bato = malloc( nbre_bato*sizeof(bateau) );
     
    	taille( nbre_bato , bato );
     
    	for(i=1;i<=nbre_bato;i++)
    	{
    		printf("bato %d = %d\n",i,(bato+i)->longueur);
    	}	
     
     return 0;
    }
    ex.h
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    void taille( int n_b , bateau *b );
    taille.c
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    #include <stdio.h>
    #include <stdlib.h>
     
    void taille( int n_b , bateau *b )
    {
    	int i;
    	for(i=1;i<=n_b;i++)
    	{
    		(b+i)->longueur = i;
    	}	
    }
    Makefile
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    ex: ex.o taille.o
     
    	gcc -o ex ex.o taille.o
     
    ex.o: ex.c ex.h
     
    	gcc -c ex.c
     
    taille.o: taille.c
     
    	gcc -c taille.c
    Quand j'utilise le commande make, il me dit:
    xxxx@xxxx:~/Bureau/ex$ make
    gcc -c ex.c
    In file included from ex.c:4:
    ex.h:2: erreur: expected declaration specifiers or «...» before «bateau»
    ex.c: Dans la fonction «main» :
    ex.c:20: erreur: trop d'arguments pour la fonction «taille»
    make: *** [ex.o] Erreur 1

    Je pense que cela vient du fait que le type bateau n'est déclaré que dans ex.c ????
    Qu'en pensez vous ??
    Merci

  5. #5
    Membre habitué
    Homme Profil pro
    Ingénieur systèmes et réseaux
    Inscrit en
    Juillet 2005
    Messages
    147
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : France, Seine Maritime (Haute Normandie)

    Informations professionnelles :
    Activité : Ingénieur systèmes et réseaux
    Secteur : High Tech - Produits et services télécom et Internet

    Informations forums :
    Inscription : Juillet 2005
    Messages : 147
    Points : 165
    Points
    165
    Par défaut
    Salut,

    En effet, la définition du type bateau est faite après l'inclusion de ex.h, ce qui fait que quand le compilateur arrive sur

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    void taille( int n_b , bateau *b );
    il ne connait pas le type bateau. Il faut donc mettre le type bateau dans le fichier .h, avant le prototype de la fonction taille.

    D'autre part, je trouve ton découpage un peu étrange. Normalement, pour une fonction avec un fichier d'entete, on donne le meme nom au fichier d'entete (.h) qui déclare la fonction et au fichier source (.c) qui implémente le corps de la fonction.

    Ce qui donne :

    ex.c
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    #include <stdio.h>
    #include <stdlib.h>
    
     
    #include "taille.h"
    
    int main(void)
    {
        int i, nbre_bato;
        bateau *bato; 
     
        printf("nbre de bato: ");
        scanf(" %d",&nbre_bato);
     
        bato = malloc( nbre_bato*sizeof(bateau) );
     
        taille( nbre_bato , bato );
     
        for(i=1;i<=nbre_bato;i++)
        {
            printf("bato %d = %d\n",i,(bato+i)->longueur);
        }    
     
     return 0;
    }
    taille.h
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    #ifndef TAILLE_H
    #define TAILLE_H
    
    typedef struct bateau_s{
        int longueur;
    } bateau;
    
    void taille( int n_b , bateau *b );
    
    #endif
    J'ai rajouté #ifndef TAILLE_H etc pour ne pas déclarer deux fois le type bateau et la fonction taille, meme si taille.h est inclu plusieurs fois

    taille.c
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    #include <stdio.h>
    #include <stdlib.h>
    
    #include "taille.h"
    
    void taille( int n_b , bateau *b )
    {
        int i;
        for(i=1;i<=n_b;i++)
        {
            (b+i)->longueur = i;
        }    
    }
    Makefile
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    ex: ex.o taille.o
     
        gcc -o ex ex.o taille.o
     
    ex.o: ex.c taille.h
     
        gcc -c ex.c
     
    taille.o: taille.c taille.h
     
        gcc -c taille.c
    Voila, j'espère pas avoir dit trop de bêtises.
    Avec les ordinateurs, 99% des bugs proviennent de l'interface chaise-clavier...

    Comment ça 1Km n'est pas égal à 1024m ???

  6. #6
    Expert éminent sénior
    Avatar de diogene
    Homme Profil pro
    Enseignant Chercheur
    Inscrit en
    Juin 2005
    Messages
    5 761
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Enseignant Chercheur
    Secteur : Enseignement

    Informations forums :
    Inscription : Juin 2005
    Messages : 5 761
    Points : 13 926
    Points
    13 926
    Par défaut
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    	bato = malloc( nbre_bato*sizeof(bateau) );
    ... 
    	for(i=1;i<=nbre_bato;i++)
    	{
    		printf("bato %d = %d\n",i,(bato+i)->longueur);
    	}
    Je te rappelle à nouveau que les indices de tableau vont de 0 pour le premier élément à (nombre d'éléments -1) pour le dernier (ici, de 0 à nbre_bato-1) !!!!
    Publication : Concepts en C

    Mon avatar : Glenn Gould

    --------------------------------------------------------------------------
    Une réponse vous a été utile ? Remerciez son auteur en cliquant le pouce vert !

  7. #7
    Membre habitué
    Homme Profil pro
    Ingénieur systèmes et réseaux
    Inscrit en
    Juillet 2005
    Messages
    147
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : France, Seine Maritime (Haute Normandie)

    Informations professionnelles :
    Activité : Ingénieur systèmes et réseaux
    Secteur : High Tech - Produits et services télécom et Internet

    Informations forums :
    Inscription : Juillet 2005
    Messages : 147
    Points : 165
    Points
    165
    Par défaut
    Exact pour les indices, j'ai fait un bête copier-coller sans relire, et je n'ai pas modifier
    Avec les ordinateurs, 99% des bugs proviennent de l'interface chaise-clavier...

    Comment ça 1Km n'est pas égal à 1024m ???

  8. #8
    Nouveau membre du Club
    Inscrit en
    Janvier 2007
    Messages
    43
    Détails du profil
    Informations forums :
    Inscription : Janvier 2007
    Messages : 43
    Points : 31
    Points
    31
    Par défaut
    C'est bon tout fonctionne (j'ai changé les indices)
    Merci à tous les trois !!!!

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. passage de gros tableaux par adresse
    Par ol9245 dans le forum MATLAB
    Réponses: 7
    Dernier message: 10/10/2012, 11h51
  2. Passage de paramètres par adresse ou par copie ?
    Par EpiTouille dans le forum Langage
    Réponses: 6
    Dernier message: 24/12/2011, 10h31
  3. [vocabulaire] passage par adresse et par valeur.
    Par debutantenalgo dans le forum Algorithmes et structures de données
    Réponses: 6
    Dernier message: 21/12/2009, 15h42
  4. Réponses: 12
    Dernier message: 26/01/2008, 20h23
  5. Passage par valeur / passage par adresse
    Par jeje99 dans le forum C++
    Réponses: 13
    Dernier message: 16/02/2006, 10h29

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo