9 memoire support

Upload: amiri1988

Post on 25-Feb-2018

215 views

Category:

Documents


0 download

TRANSCRIPT

  • 7/25/2019 9 Memoire Support

    1/115

    Allocation dynamique de tableaux et de structures

  • 7/25/2019 9 Memoire Support

    2/115

    Mmoire

    La mmoire d'un ordinateur est compose d'un grand nombre d'octets(une valeurentre 0 et 255) :

    Chaque octet est repr par une adresse, qui est un nombre entier.

    adresse octet

    0

    1

    23

    !

    2

  • 7/25/2019 9 Memoire Support

    3/115

    Les variables sont stockes en mmoire. Par exemple:

    int a(3);

    adresse contenu

    24996

    25000

    25004 ?

    25008 ?

    25012 ?

    25016 ?

    25020

    a3

  • 7/25/2019 9 Memoire Support

    4/115

    On peut obtenir l'adresse d'une variable grce l'oprateur &:

    Par exemple:

    int a(3);

    cout

  • 7/25/2019 9 Memoire Support

    5/115

    En C et en C++, on peut dfinir des variables pour qu'elles contiennentdes adresses.

    Pour dclarer une telle variable, Il faut ajouter une toile *entre le type

    et le nom de la variable:

    int *p;

    pest appel unpointeur.

    Stocker une adresse dans une variable

  • 7/25/2019 9 Memoire Support

    6/115

    Si on fait:

    int * p;

    p = &a;

    pcontient l'adresse de a.

    Stocker une adresse dans une variable

    adresse contenu

    24996

    25000

    25004 ?

    25008

    25012

    25016

    25108

    a

    p

    3

    ?

    25004

  • 7/25/2019 9 Memoire Support

    7/115

    pcontient l'adresse de a.

    On dit que ppointe sur a.

    La valeur de l'adresse de a n'est pasimportante en elle-mme, ce qui est

    important est que ppointe sur a.

    Ceci est souvent reprsent par une flcheallant de p a.

    Reprsentation graphique (1)

    adresse contenu

    24996

    25000

    25004 ?

    25008

    25012

    25016

    25108

    a

    p

    3

  • 7/25/2019 9 Memoire Support

    8/115

    On n'a gnralement pas besoin de la reprsentation de la mmoire, et

    on peut ne garder que la reprsentation des variables.

    int a(3);

    int * p;

    p = &a;

    Reprsentation graphique (2)

    a

    p

    3

  • 7/25/2019 9 Memoire Support

    9/115

    L'oprateur *permet d'accder la valeur stocke une adresse:

    cout

  • 7/25/2019 9 Memoire Support

    10/115

    On peut aussi utiliser l'oprateur pour modifier une valeur pointe parun pointeur:

    int a(3);

    int * p;

    p = &a;

    *p = 5;

    Modifier la valeur pointe par un pointeur

    5a

    p

    3

  • 7/25/2019 9 Memoire Support

    11/115

    l'toile utilise pour dclarer un pointeur:

    int * p;

    et l'toile pour obtenir la valeur pointe par le pointeur:

    *p = 5;

    Attention ne pas confondre

    Mme symbole (*) maissignification diffrente.

  • 7/25/2019 9 Memoire Support

    12/115

    Rsum

    Un pointeur est une variable. On dclare un pointeur en mettant une

    toile (*) entre le type et le nom du pointeur:

    int * p;

    Un pointeur contient une adresse.

    On peut obtenir l'adresse d'une variable avec l'oprateur &:

    int a = 0;

    p = &a;

    L'oprateur *permet d'accder la mmoire pointe par un pointeur:

    int b = *p;

    *p = 1;

    a

    p

    0

    b

    0

    1

  • 7/25/2019 9 Memoire Support

    13/115

    Dclaration d'un pointeur

    Un pointeur est une variable:On peut dclarer plusieurs pointeurs sur une mme ligne, et initialiser

    un pointeur lors de sa dclaration. Exemples:

    double a;

    double * p1(&a);

    int * p2, * p3;

    Attention: pour dclarer plusieurs pointeurs sur une mme ligne, ilfaut rpterl'toile. Si on fait:

    int * p2, p3; // !!

    p2est de type pointeur sur int, mais p3est une variable classique,de type int.

  • 7/25/2019 9 Memoire Support

    14/115

    Le pointeur NULLou 0

    On utilise parfois la valeur 0, ou la constante NULL(de type pointeur, qui vaut

    0) pour initialiser un pointeur:int * p = 0;

    ou

    int * p = NULL;

    L'adresse 0n'est jamais utilise pour stocker des variables, elle correspond

    donc toujours une adresse invalide: Si on essaie d'accder la valeurpointe par pen faisant par exemple:

    int * p = 0;

    int a = *p;

    *p = 12;

    on provoque un:

    Segmentation fault

    L'intrt du pointeur NULL est par exemple de signaler qu'une fonction n'a

    pas pu fonctionner correctement, ou qu'un pointeur ne contient pas une

    adresse valide.

  • 7/25/2019 9 Memoire Support

    15/115

    On peut voir l'oprateur *comme l'inverse de l'oprateur &:

    b = *(&a);

    est quivalent

    b = a;

    On peut mettre zro, un ou plusieurs espaces avant et aprs l'toile et

    le et commercial:

    int *pa = & a;

    b = * pa;

    Remarques

  • 7/25/2019 9 Memoire Support

    16/115

  • 7/25/2019 9 Memoire Support

    17/115

    int n(1), p(2);int * ad1, * ad2;

    ad1 = &n;

    ad2 = &p;

    *ad1 = *ad2 + 3;ad1 = ad2;

    *ad1 = *ad2 + 5;

    Pas--pas

    ad2ad1

    n p

    1 2

  • 7/25/2019 9 Memoire Support

    18/115

    int n(1), p(2);int * ad1, * ad2;

    ad1 = &n;

    ad2 = &p;

    *ad1 = *ad2 + 3;ad1 = ad2;

    *ad1 = *ad2 + 5;

    Pas--pas

    ad2ad1

    n p

    1 2

    ad1pointe sur n

  • 7/25/2019 9 Memoire Support

    19/115

    int n(1), p(2);int * ad1, * ad2;

    ad1 = &n;

    ad2 = &p;

    *ad1 = *ad2 + 3;ad1 = ad2;

    *ad1 = *ad2 + 5;

    Pas--pas

    ad2ad1

    n p

    1 2

    ad2pointe sur p

  • 7/25/2019 9 Memoire Support

    20/115

    int n(1), p(2);int * ad1, * ad2;

    ad1 = &n;

    ad2 = &p;

    *ad1 = *ad2 + 3;ad1 = ad2;

    *ad1 = *ad2 + 5;

    Pas--pas

    ad2ad1

    n p

    1 2

    exactement comme n = p + 3;ncontient maintenant 5

    5

  • 7/25/2019 9 Memoire Support

    21/115

    int n(1), p(2);int * ad1, * ad2;

    ad1 = &n;

    ad2 = &p;

    *ad1 = *ad2 + 3;ad1 = ad2;

    *ad1 = *ad2 + 5;

    Pas--pas

    ad2ad1

    n p25

  • 7/25/2019 9 Memoire Support

    22/115

    int n(1), p(2);int * ad1, * ad2;

    ad1 = &n;

    ad2 = &p;

    *ad1 = *ad2 + 3;ad1 = ad2;

    *ad1 = *ad2 + 5;

    Pas--pas

    ad2ad1

    n p2

    ad1et ad2pointent maintenant tous lesdeux sur p.

    5

  • 7/25/2019 9 Memoire Support

    23/115

    int n(1), p(2);int * ad1, * ad2;

    ad1 = &n;

    ad2 = &p;

    *ad1 = *ad2 + 3;ad1 = ad2;

    *ad1 = *ad2 + 5;

    Pas--pas

    ad2ad1

    n p2

    exactement comme p = p + 5;

    pcontient donc maintenant 7

    5

  • 7/25/2019 9 Memoire Support

    24/115

    Exerciceint a(2), b(5);

    int * p;

    p = &a;

    cout

  • 7/25/2019 9 Memoire Support

    25/115

    Pointeur en paramtre d'une fonction

  • 7/25/2019 9 Memoire Support

    26/115

    Rappel

    Si on excute:

    void mis_a_zero(int a){

    a = 0;}

    int main(){

    int n = 10;

    mis_a_zero(n);

    cout

  • 7/25/2019 9 Memoire Support

    27/115

    Pas--pas

    void mis_a_zero(int a){a = 0;

    }

    int main(){int n = 10;

    cout

  • 7/25/2019 9 Memoire Support

    28/115

    Pas--pas

    void mis_a_zero(int a){a = 0;

    }

    int main(){int n = 10;

    cout

  • 7/25/2019 9 Memoire Support

    29/115

    Pas--pas

    void mis_a_zero(int a){a = 0;

    }

    int main(){int n = 10;

    cout

  • 7/25/2019 9 Memoire Support

    30/115

    Pas--pas

    void mis_a_zero(int a){a = 0;

    }

    int main(){int n = 10;

    cout

  • 7/25/2019 9 Memoire Support

    31/115

    Pas--pas

    void mis_a_zero(int a){a = 0;

    }

    int main(){int n = 10;

    cout

  • 7/25/2019 9 Memoire Support

    32/115

    Pour que la fonction puisse modifier la variable n, il y a deux options en

    C++:

    soit utiliser un passage par rfrence,

    soit utiliser un pointeur.

    Nous avons dj vu le passage par rfrence. Nous allons voir la

    solution avec un pointeur.

    Une fonction modifiantune variable passe en paramtre

  • 7/25/2019 9 Memoire Support

    33/115

    Pour que la fonction puisse modifier la variable n, il faut passer enparamtre l'adresse de la variable plutt que sa valeur:

    void mis_a_zero(int* pa){*pa = 0;

    }

    int main(){int n = 10;

    mis_a_zero(&n);

    cout

  • 7/25/2019 9 Memoire Support

    34/115

    void mis_a_zero(int * pa){*pa = 0;

    }

    int main(){int n = 10;

    mis_a_zero(&n);

    cout

  • 7/25/2019 9 Memoire Support

    35/115

    void mis_a_zero(int * pa){*pa = 0;

    }

    int main(){int n = 10;

    mis_a_zero(&n);

    cout

  • 7/25/2019 9 Memoire Support

    36/115

    void mis_a_zero(int * pa){*pa = 0;

    }

    int main(){int n = 10;

    mis_a_zero(&n);

    cout

  • 7/25/2019 9 Memoire Support

    37/115

    void mis_a_zero(int * pa){*pa = 0;

    }

    int main(){int n = 10;

    mis_a_zero(&n);

    cout

  • 7/25/2019 9 Memoire Support

    38/115

    void mis_a_zero(int * pa){*pa = 0;

    }

    int main(){int n = 10;

    mis_a_zero(&n);

    cout

  • 7/25/2019 9 Memoire Support

    39/115

    void mis_a_zero(int * pa){*pa = 0;

    }

    int main(){int n = 10;

    mis_a_zero(&n);

    cout

  • 7/25/2019 9 Memoire Support

    40/115

    void f(int * p, int q)

    {*p = *p + q;}

    void g(int * r){f(r, 1);

    }

    int a = 0, b = 2;f(&a, b);cout

  • 7/25/2019 9 Memoire Support

    41/115

    Une fonction peut modifierles lments d'un tableau

    pass en paramtre

  • 7/25/2019 9 Memoire Support

    42/115

    Utilis seul, le nom du tableau correspond l'adresse du premierlment.

    Par exemple, on peut faire:

    int T[5];

    int * tab = T;

    et tabpointe alors sur le premier lment de T.

    Attention, Tn'est pas pour autant un pointeur.

    On ne peut pas faire par exemple:T = &a;

    si Ta t dclar comme un tableau.

    Tableaux et pointeurs

    adresse contenu

    19996

    T= 20000 T[0]

    20004 T[1]

    20008 T[2]

    20012 T[3]

    20016 T[4]

    20020

    tab

  • 7/25/2019 9 Memoire Support

    43/115

    Aprs:

    int T[5];int * tab = T;

    tabpointe sur le premier lment de T.

    *tabcorrespond donc T[0], le premier lment de T.

    tab + 1est l'adresse du deuxime lment de T.

    *(tab + 1) correspond donc T[1], le deuximelment de T.

    etc...

    Tableaux et pointeurs

    adresse contenu

    19996

    T= 20000 T[0]

    20004 T[1]

    20008 T[2]

    20012 T[3]

    20016 T[4]

    20020

    tab

  • 7/25/2019 9 Memoire Support

    44/115

    Notez que:

    Si

    tabvaut 20000,

    et si tabest un pointeur sur int

    Alors

    tab + 1vaut 20004

    pour pointer sur le int suivant: un int est reprsent sur 4 octets, et les adressessont dfinies en octet.

    Ce mcanisme de calcul simplifie l'accs aux lments du tableau: il n'y a pas savoirqu'il faut multiplier par 4 dans le cas des int, par 8 dans le cas des double, etc...

  • 7/25/2019 9 Memoire Support

    45/115

    Aprs:

    int T[5];int * tab = T;

    tabpointe sur le premier lment de T.

    *tabcorrespond donc T[0], le premier lment de T.

    tab + 1est l'adresse du deuxime lment de T.

    *(tab + 1)correspond donc T[1], le deuxime lment de T.

    On peut galement crire tab[1] la place de *(tab + 1).

    Tableaux et pointeurs

    adresse contenu

    19996

    T= 20000 T[0]

    20004 T[1]

    20008 T[2]

    20012 T[3]

    20016 T[4]20020

    tab

  • 7/25/2019 9 Memoire Support

    46/115

    En C et en C++, on peut crire

    tab[i]

    la place de

    *(tab + i)

    ce qui permet d'utiliser tab comme on utiliserait un

    tableau!

  • 7/25/2019 9 Memoire Support

    47/115

    int T[10];

    for(int i = 0; i < 10; i++)

    T[i] = i * i;

    int * p = T, * q = &(T[2]);

    cout

  • 7/25/2019 9 Memoire Support

    48/115

    Supposons qu'on veut crire une fonction qui ajoute 1 aux lments d'un

    tableau. On peut donc crire cette fonction comme a:

    void ajoute1_aux_elements(int * tab){

    for(int i(0); i < 5; ++i) {*(tab + i) = *(tab + i) + 1;

    }}

    ou comme a:

    void ajoute1_aux_elements(int * tab){for(int i(0); i < 5; ++i) {

    tab[i]= tab[i] + 1;}

    }

    et on peut appeler cette fonction ainsi:

    int T[5];ajoute1_aux_elements(T);

    Accs aux lments d'un tableau

    adresse contenu

    19996

    T= 20000 T[0]

    20004 T[1]

    20008 T[2]

    20012 T[3]

    20016 T[4]

    20020

    tab

  • 7/25/2019 9 Memoire Support

    49/115

    void ajoute1_aux_elements(int * tab){for(int i(0); i < 5; ++i) {tab[i]= tab[i] + 1;

    }}

    ...

    int T[5];

    ajoute1_aux_elements(T);

    adresse contenu

    19996

    T= 20000 T[0]

    20004 T[1]

    20008 T[2]

    20012 T[3]

    20016 T[4]

    20020

  • 7/25/2019 9 Memoire Support

    50/115

    void ajoute1_aux_elements(int * tab){for(int i(0); i < 5; ++i) {tab[i]= tab[i] + 1;

    }}

    ...

    int T[5];

    ajoute1_aux_elements(T);

    adresse contenu

    19996

    T= 20000 T[0]

    20004 T[1]

    20008 T[2]

    20012 T[3]

    20016 T[4]

    20020

    tab

  • 7/25/2019 9 Memoire Support

    51/115

    void ajoute1_aux_elements(int * tab){for(int i(0); i < 5; ++i) {tab[i]= tab[i] + 1;

    }}

    ...

    int T[5];

    ajoute1_aux_elements(T);

    adresse contenu

    19996

    T= 20000 T[0]

    20004 T[1]

    20008 T[2]

    20012 T[3]20016 T[4]

    20020

    tab

    i

  • 7/25/2019 9 Memoire Support

    52/115

    void ajoute1_aux_elements(int * tab){for(int i(0); i < 5; ++i) {tab[i]= tab[i] + 1;

    }}

    ...

    int T[5];

    ajoute1_aux_elements(T);

    adresse contenu

    19996

    T= 20000 T[0]

    20004 T[1]

    20008 T[2]

    20012 T[3]20016 T[4]

    20020

    tab

  • 7/25/2019 9 Memoire Support

    53/115

    void ajoute1_aux_elements(int * tab){for(int i(0); i < 5; ++i) {tab[i]= tab[i] + 1;

    }}

    ...

    int T[5];

    ajoute1_aux_elements(T);

    adresse contenu

    19996

    T= 20000 T[0]

    20004 T[1]

    20008 T[2]

    20012 T[3]20016 T[4]

    20020

    tab

  • 7/25/2019 9 Memoire Support

    54/115

    On peut crire indiffremment:

    void ajoute1_aux_elements(int tab[5])

    ou

    void ajoute1_aux_elements(int * tab)

    Le 5du premier en-tte N'est PAS considr par le compilateur.

    On peut mme crire:

    void ajoute1_aux_elements(int tab[])

  • 7/25/2019 9 Memoire Support

    55/115

    On peut crire indiffremment:

    void ajoute1_aux_elements(int tab[5])

    ou

    void ajoute1_aux_elements(int * tab)

    Le 5du premier en-tte N'est PAS considr par le compilateur.

    On peut mme crire:

    void ajoute1_aux_elements(int tab[])

    Utilisez cette notation

  • 7/25/2019 9 Memoire Support

    56/115

    Attention au nombre d'lments

    La fonction

    void ajoute1_aux_elements(int * tab)

    ne connat PAS LA TAILLE du tableau pass en paramtre.

  • 7/25/2019 9 Memoire Support

    57/115

    Passer le nombre d'lments en paramtre

    Pour que la fonction puisse tre utilise pour n'importe quel tableau, quelle

    que soit sa taille, on peut passer la taille du tableau en paramtre.

    Exemple:

    void ajoute1_aux_elements(int * tab, int nb_elements)

    {

    for(int i(0); i

  • 7/25/2019 9 Memoire Support

    58/115

    Exercicevoid f(int * q, int r){q = q + r;*q = 0;

    }

    void g(int * q, int r){q[r] = 0;

    }

    ...

    int T[4] = {1, 5, 6, 9};int * p = T;

    *p = *p + 1;cout

  • 7/25/2019 9 Memoire Support

    59/115

    Allocation dynamique:

    Allouer de la mmoire

    pendant l'excution du programme

  • 7/25/2019 9 Memoire Support

    60/115

    On peut allouer de la mmoire pendant l'excution du programme.

    On parle d'Allocation dynamique.

    L'allocation se fait avec l'instruction new.

    Une fois que la mmoire alloue n'est plus utile, IL FAUT la librer,

    avec l'instruction delete.

    Allouer de la mmoire

    pendant l'excution du programme

  • 7/25/2019 9 Memoire Support

    61/115

    int * tab;

    tab = new int[5];

    L'instruction newfait 2 choses:

    1.

    Elle alloue de la mmoire, c'est--dire qu'ellerserve une partie de la mmoire de l'ordinateurpour que le programme puisse l'utiliser.

    Allouer de la mmoirependant l'excution du programme

    mmoire

    tab

  • 7/25/2019 9 Memoire Support

    62/115

    int * tab;

    tab = new int[5];

    L'instruction newfait 2 choses:

    1.

    Elle alloue de la mmoire, c'est--dire qu'ellerserve une partie de la mmoire de l'ordinateurpour que le programme puisse l'utiliser.

    2. Elle renvoie l'adresse du dbut de cettemmoire.

    Dans notre exemple, tabva donc pointer sur

    cette mmoire, et permettre au programme del'utiliser.

    Allouer de la mmoirependant l'excution du programme

    mmoire

    tab

  • 7/25/2019 9 Memoire Support

    63/115

    int * tab;

    tab = new int[5];

    tab[2] = 10;tab[3] = 5 * tab[2];

    delete [] tab;

    L'instruction deletelibre la mmoire alloue

    par new, c'est--dire que cette partie de lammoire va pouvoir tre utilise par d'autres

    programmes.

    Le programme n'a plus le droit d'accder

    cette partie de la mmoire.

    Allouer de la mmoirependant l'excution du programme

    mmoire

    tab

  • 7/25/2019 9 Memoire Support

    64/115

    Allocation de la mmoire:

    tab = new int [5];

    Libration de la mmoire:

    delete [] tab;

    newet delete

  • 7/25/2019 9 Memoire Support

    65/115

    Allocation de la mmoire:

    tab = new int [5];

    Libration de la mmoire:

    delete [] tab;

    newet delete

    Nombre d'lments allouer

    Retourne l'adresse dupremier lment allou:

    Tdoit tre dclarcomme un pointeur sur

    int.

    Attention ne pasoublier les crochets [ ]

    Adresse de dbut dela mmoire librer

    Type des lments

  • 7/25/2019 9 Memoire Support

    66/115

    void set(int * tab, int nb_elements, int v){for(int i(0); i < nb_elements; ++i) {tab[i] = v;

    }}

    int main()

    {int * T;int n;

    cout n;

    T = new int[n];

    // On met tous les elements de T a 0

    set(T, n, 0);

    //..

    // il ne faut pas oublier de liberer la memoire allouee pour T

    delete [] T;

    return 0;}

  • 7/25/2019 9 Memoire Support

    67/115

    Fonction qui alloue un tableau

    int * cree_tableau(int nb_elements){int * T;

    T = new int[nb_elements];return T;}

    Le rsultat de la fonction est un pointeur sur le premierlment du tableau.

    Exemple d'utilisation:int * T = cree_tableau(10);

  • 7/25/2019 9 Memoire Support

    68/115

    Fonction qui alloue un tableau

    int * cree_tableau(int nb_elements){int * T;

    T = new int[nb_elements];return T;}

    Le rsultat de la fonction est un pointeur sur le premierlment du tableau.

    Exemple d'utilisation:int * T = cree_tableau(10);

    le rsultat de la fonction est

    de type pointeur sur int

    la fonction renvoie l'adresse dupremier lment du tableau

  • 7/25/2019 9 Memoire Support

    69/115

    On peut aussi crire cree_tableaude faon plus directe:

    int * cree_tableau(int nb_elements){return new int[nb_elements];

    }

    L t d l f ti t h t

  • 7/25/2019 9 Memoire Support

    70/115

    Le type de la fonction est cohrent

    avec le type de son rsultat

    int * cree_tableau(int nb_elements){int * T;T = new int[nb_elements];return T;

    }

    int * cree_tableau(int nb_elements){return new int[nb_elements];

    }

    Test un pointeur sur int

    L'expressionnew int[nb_elements]est

    un pointeur sur int

  • 7/25/2019 9 Memoire Support

    71/115

    Autre fonction qui alloue un tableau

    Fonction qui alloue et remplit un tableau avec des valeurs alatoires:

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    Exemple d'utilisation:int * T = cree_tableau_aleatoire(5, 100);

  • 7/25/2019 9 Memoire Support

    72/115

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    int * T = cree_tableau_aleatoire(5, 100);

  • 7/25/2019 9 Memoire Support

    73/115

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    int * T = cree_tableau_aleatoire(5, 100);

    5 1

  • 7/25/2019 9 Memoire Support

    74/115

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    int * T = cree_tableau_aleatoire(5, 100);

    5 1

    mmoire

    ?

    ?

    ?

    ??

  • 7/25/2019 9 Memoire Support

    75/115

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    int * T = cree_tableau_aleatoire(5, 100);

    5 1

    mmoire

    ?

    ?

    ?

    ??

    resultat

  • 7/25/2019 9 Memoire Support

    76/115

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    int * T = cree_tableau_aleatoire(5, 100);

    5 1

    mmoire

    56

    34

    82

    1739

    resultat

  • 7/25/2019 9 Memoire Support

    77/115

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    int * T = cree_tableau_aleatoire(5, 100);

    5 1

    mmoire

    56

    34

    82

    1739

    resultat

  • 7/25/2019 9 Memoire Support

    78/115

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    int * T = cree_tableau_aleatoire(5, 100);

    mmoire

    56

    34

    82

    1739

  • 7/25/2019 9 Memoire Support

    79/115

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    int * T = cree_tableau_aleatoire(5, 100);

    mmoire

    56

    34

    82

    1739

    resultat

  • 7/25/2019 9 Memoire Support

    80/115

    int * cree_tableau_aleatoire(int nb_elements, int val_max){int * resultat = new int[nb_elements];

    for(int i(0); i < nb_elements; ++i) {resultat[i] = rand() % val_max;

    }

    return resultat;}

    int * T = cree_tableau_aleatoire(5, 100);

    mmoire

    56

    34

    82

    1739

    resultat

  • 7/25/2019 9 Memoire Support

    81/115

    Allocation dynamique de

    structures

  • 7/25/2019 9 Memoire Support

    82/115

    struct Chat

    { string nom;double poids;

    };

    ...

    Chat * c = new Chat;

    delete c;

    Allocation d'une structure

    c: pointeur sur Chat

    alloue de la mmoire pour une

    seule structure Chat

    libre la mmoire pointe par c

  • 7/25/2019 9 Memoire Support

    83/115

    struct Chat

    { string nom;double poids;

    };

    ...

    Chat * c = new Chat;

    Allocation d'une structure

    poids

    0.0

    nom

  • 7/25/2019 9 Memoire Support

    84/115

    struct Chat

    { string nom;double poids;

    };

    ...

    Chat * c = new Chat;

    Allocation d'une structure

    poids

    0.0

    nom

    c

  • 7/25/2019 9 Memoire Support

    85/115

    struct Chat

    { string nom;double poids;

    };

    ...

    Chat * c = new Chat;

    (*c).poids = 2.5;

    Accder aux champs

    poids

    2.5

    nom

    c

    L' t

  • 7/25/2019 9 Memoire Support

    86/115

    La notation

    (*c).poids

    n'est pas trs lisible.

    Il existe un oprateur, not ->(un signe moins -, un signe suprieur

    >), qui permet d'crire des expressions quivalentes mais plus lisibles:

    c->poids

    L'oprateur ->

    c->poids est quivalent (*c).poids

    ou > ?

  • 7/25/2019 9 Memoire Support

    87/115

    A gauche de.on trouve forcment une variablede type structure:Chat c;

    c.poids = 2.5;

    A gauche de ->on trouve forcment unpointeursur structure:

    Chat * pc = &c;

    pc->poids = 2.5;

    .ou ->?

    Messages d'erreur

  • 7/25/2019 9 Memoire Support

    88/115

    A la compilation de:

    Chat c;

    c->poids = 2.5; // !!on obtient l'erreur:

    error: base operand of `->' has non-pointer type `Chat'

    cn'est pas un pointeur et appliquer l'oprateur ->sur cn'a donc pas de sens.

    A la compilation de:

    Chat * pc;pc.poids = 2.5; // !!on obtient l'erreur:

    error: request for member `poids' in `pc', which is of non-classtype `Chat*'

    L'oprateur. s'applique sur une structure, pas un pointeur commepcest ici.

    Messages d erreur

  • 7/25/2019 9 Memoire Support

    89/115

    Fonction qui alloue une structure

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

    le rsultat de la fonction estde type pointeur sur Chat

    la fonction renvoie l'adresse de

    la structure alloue

  • 7/25/2019 9 Memoire Support

    90/115

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

  • 7/25/2019 9 Memoire Support

    91/115

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

    "Felix" 2.5

  • 7/25/2019 9 Memoire Support

    92/115

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

    "Felix" 2.5

  • 7/25/2019 9 Memoire Support

    93/115

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

    "Felix" 2.5

    poids

    0.0

    nom

    c

  • 7/25/2019 9 Memoire Support

    94/115

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

    "Felix" 2.5

    poids

    0.0

    c

    nom f e l i x

  • 7/25/2019 9 Memoire Support

    95/115

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

    "Felix" 2.5

    poids

    2.5

    c

    nom f e l i x

  • 7/25/2019 9 Memoire Support

    96/115

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

    "Felix" 2.5

    poids

    2.5

    c

    nom f e l i x

  • 7/25/2019 9 Memoire Support

    97/115

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

    poids

    2.5

    nom f e l i x

  • 7/25/2019 9 Memoire Support

    98/115

    Chat * cree_chat(string nom, double poids){Chat * c = new Chat;

    c->nom = nom;c->poids = poids;

    return c;}

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 2.5);

    poids

    2.5

    nom f e l i x

    g

    Pointeur sur structure en paramtre

  • 7/25/2019 9 Memoire Support

    99/115

    Pointeur sur structure en paramtre

    d'une fonction

    void demande_poids(Chat * chat){cout chat->poids;

    }

    Exemple d'utilisation:

    Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

  • 7/25/2019 9 Memoire Support

    100/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    poids

    0.0

    nom f e l i x

    g

  • 7/25/2019 9 Memoire Support

    101/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    poids

    0.0

    nom f e l i x

    g

  • 7/25/2019 9 Memoire Support

    102/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    poids

    0.0

    nom f e l i x

    g

    chat

  • 7/25/2019 9 Memoire Support

    103/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    poids

    0.0

    nom f e l i x

    g

    chat

  • 7/25/2019 9 Memoire Support

    104/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    poids

    0.0

    nom f e l i x

    g

    chat

  • 7/25/2019 9 Memoire Support

    105/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    poids

    2.5

    nom f e l i x

    g

    chat

  • 7/25/2019 9 Memoire Support

    106/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    poids

    2.5

    nom f e l i x

    g

  • 7/25/2019 9 Memoire Support

    107/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    g2

    poids

    ?

    nom

  • 7/25/2019 9 Memoire Support

    108/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    g2

    poids

    ?

    nom G a r f i e l d

  • 7/25/2019 9 Memoire Support

    109/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    g2

    poids

    ?

    nom G a r f i e l d

  • 7/25/2019 9 Memoire Support

    110/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    g2

    poids

    ?

    nom G a r f i e l d

    chat

  • 7/25/2019 9 Memoire Support

    111/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    g2

    poids

    ?

    nom G a r f i e l d

    chat

  • 7/25/2019 9 Memoire Support

    112/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    g2

    poids

    ?

    nom G a r f i e l d

    chat

  • 7/25/2019 9 Memoire Support

    113/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    g2

    poids

    3.2

    nom G a r f i e l d

    chat

  • 7/25/2019 9 Memoire Support

    114/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2.nom = "Garfield";demande_poids(&g2);

    g2

    poids

    3.2

    nom G a r f i e l d

    chat

  • 7/25/2019 9 Memoire Support

    115/115

    void demande_poids(Chat * chat)

    {cout chat->poids;

    }

    Exemple d'utilisation:Chat * g = cree_chat("Felix", 0.0);demande_poids(g);

    Chat g2;g2 nom = "Garfield";

    g2

    poids

    3.2

    nom G a r f i e l d