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 :

Addition sur des entiers longs


Sujet :

C

  1. #1
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut Addition sur des entiers longs
    Bonjour,
    Je dois faire plusieurs opérations sur des entiers longs. Mais je bloque déjà à l'opération.
    J'ai crée un type Entier_long qui contient un signe, une taille, et un tableau dans lequel est stocké chaque chiffre de mon entier long.

    Je n'arrive pas trop m'en sortir, car il faut gérer plusieurs points :
    -la taille des 2 entiers à comparer
    -leur signe respectif
    -le cas d'une retenue en plein milieu du nombre, mais aussi dans le cas où la retenue fait "grandir" la taille du nombre de +1.
    -J'en oublie peut-être...

    J'ai fait une multitude de tests, mais aucun n'était bon.
    Je laisse une esquisse du dernier que j'ai testé, ça se trouve je suis sur la bonne voie...

    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
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
     
    void Addition (Entier_long a, Entier_long b)
    {
        int taille_1=0, taille_2=0;
        int reste=0, i=0, s;
        int Max=0, Min=0;
        taille_1=a.taille;
        taille_2=b.taille;
        Entier_long NbGrand, NbPetit;
        int somme[Max+2];
     
        if(taille_1>=taille_2) 
        {
            Max=taille_1;
            Min=taille_2;
            NbGrand=a;
            NbPetit=b;
     
        }
        else
        {
            Max=taille_2;
            Min=taille_1;
            NbGrand=b;
            NbPetit=a;
        }
     
        for(i=0;i<Min;i++)
        {
            s=NbGrand.Chiffres_sign[i]+NbPetit.Chiffres_sign[i]+reste;
            reste=s/10;
            s=s%10;
            somme[i]=s;
        }
        for(i=Min;i<Max;i++)
        {
            s=NbGrand.Chiffres_sign[Max]+reste;
            reste=s/10;
            s=s%10;
            somme[i]=s;
        }
     
        /* Affichage de l'addition */
        for(i=1;i<Max+1;i++)
        {
            printf("%d", somme[i]);
        }
    }
    J'ai tourné le problème dans divers sens, donc la méthode que je propose n'est peut-être pas la bonne, c'est la dernière que j'ai testé.( dans ce code je ne m'occupe pas encore des signes, si j'arrive déjà à additionner 2 nombres positifs ce sera un bon début)
    Est-ce que quelqu'un pourrait m'aider ou me guider ?
    Je peux afficher d'autres parties de mon code si besoin.

    Merci d'avance !

  2. #2
    Membre Expert

    Homme Profil pro
    Responsable des études
    Inscrit en
    Mars 2009
    Messages
    553
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Responsable des études
    Secteur : Industrie

    Informations forums :
    Inscription : Mars 2009
    Messages : 553
    Par défaut
    Hello,

    Il manque une info importante: le détail de ta structure "Entier_long" et surtout comment tu renseignes tous les champs.

    Le point sensible de ton code c'est: comment sont rangés les chiffres ? D'après ce que tu as déjà codé, il est impératif que le chiffre des unités soit dans Chiffres_sign[0], le chiffre des dizaines dans Chiffres_sign[1], etc ... C'est-à-dire dans l'ordre inverse de celui dans lequel on écrit les nombres.

    Par ailleurs, ta boucle d'affichage a un offset de 1 case, je n'ai pas compris pourquoi!

  3. #3
    Membre Expert
    Inscrit en
    Mars 2005
    Messages
    1 431
    Détails du profil
    Informations forums :
    Inscription : Mars 2005
    Messages : 1 431
    Par défaut
    Pour rebondir sur les conseils de nnovic, es-tu assuré du bon fonctionnement du reste du programme que nous n'avons pas ici ? Je veux dire, la toute première version validée (les « fondations ») devrait ressembler à quelque chose de ce genre :
    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
    #include <stdio.h>
    #include <stdlib.h>
     
    typedef struct {
        // ...
    } longint;
     
    int longint_create(longint *i) {
        // ...
    }
     
    void longint_destroy(longint *i) {
        // ...
    }
     
    void longint_set(longint *dst, long value) {
        // ...
    }
     
    void longint_print(FILE *stream, const longint *i) {
        // ...
    }
     
    int main(int argc, char *argv[]) {
        longint i;
        if (longint_create(&i) != 0)
            return 1;
     
        longint_print(stdout, &i);
     
        longint_set(&i, 16549823l);
        longint_print(stdout, &i);
     
        longint_destroy(&i);
        return 0;
    }

  4. #4
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut
    Bonjour,

    Tout d'abord merci pour vos 2 réponses.

    Concernant la déclaration de la structure, voici son code :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    typedef struct
    {
        char signe;
        int taille;
        int	Chiffres_sign[Dim]; /* Dim vaut 400, il y a un define Dim 400 en haut du programme */ 
    }Entier_long;
    Ensuite, pour remplir mon Chiffre_sign[], je fais une boucle de 0 à x.taille (x.taille exclut) donc si mon nombre est 123, je rentre le 1, puis le 2, puis le 3. Du coup en faisant comme ça, mon chiffre des unités se trouve dans la dernière case, ça parait plus logique de faire comme ceci, que de rentrer un nombre à l'envers ?
    Durant mes divers essais, j'avais également fait des essais avec des boucles partant de la fin jusqu'au début du nombre, mais ce n'était pas concluant. Dans mon cas, c'était cette méthode à adopter ?
    Concernant le "Max+1", c'était un peu expérimental, mais c'était fait pour le cas où le résultat est plus long (en taille) que mes 2 nombres à additionner.

    Le reste du programme fonctionne oui, enfin il fait ce que je souhaite (c'est-à-dire comparer mes 2 nombres, afficher l'opération souhaitée, ...) . Mais ce n'est cependant pas exactement comme le tien, Matt_Houston.

  5. #5
    Membre Expert

    Homme Profil pro
    Responsable des études
    Inscrit en
    Mars 2009
    Messages
    553
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Responsable des études
    Secteur : Industrie

    Informations forums :
    Inscription : Mars 2009
    Messages : 553
    Par défaut
    Citation Envoyé par Stéphanois57 Voir le message
    Ensuite, pour remplir mon Chiffre_sign[], je fais une boucle de 0 à x.taille (x.taille exclut) donc si mon nombre est 123, je rentre le 1, puis le 2, puis le 3. Du coup en faisant comme ça, mon chiffre des unités se trouve dans la dernière case, ça parait plus logique de faire comme ceci, que de rentrer un nombre à l'envers ?
    Fais une addition avec un papier et un stylo, tu verras que tu commences bien par additionner les chiffres par la fin. D'abord les unités, ensuite les dizaines, puis les centaines... Concentre-toi sur ça pour commencer.

  6. #6
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut
    Oui oui ça je sais, j'avais déjà fait, mais je ne parvenais pas à ce que je voulais.
    Je crois que j'avais écris quelque chose comme ça :
    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
    38
    39
    40
    41
    42
     
    void Addition (Entier_long a, Entier_long b)
    {
        int taille_1=0, taille_2=0;
        int reste=0, i=0, s;
        int Max=0, Min=0;
        taille_1=a.taille;
        taille_2=b.taille;
        int Somme[Max+2];
     
        if(taille_1>=taille_2)
        {
            Max=taille_1;
            Min=taille_2;
     
        }
        else
        {
            Max=taille_2;
            Min=taille_1;
        }
     
        for (i=Max ; i>0 ; i--)
        {
            s=a.Chiffres_sign[i]+b.Chiffres_sign[i]+reste;
            if (s>9)
            {
                Somme[i]=s%10;
                reste=1;
            }
            else
            {
                Somme[i]=s;
                reste=0;
            }
        }
        /* Affichage de l'addition */
        for(i=0;i<Max+2;i++)
        {
            printf("%d", Somme[i]);
        }
    }
    Le principe est bien comme ça ?

    Le problème en faisant ça, c'est que si les 2 nombres n'ont pas la même taille il y un a.Chiffres_sign[i] ou b.Chiffres_sign[i] qui n'existe pas.

  7. #7
    Membre Expert

    Homme Profil pro
    Responsable des études
    Inscrit en
    Mars 2009
    Messages
    553
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Responsable des études
    Secteur : Industrie

    Informations forums :
    Inscription : Mars 2009
    Messages : 553
    Par défaut
    Citation Envoyé par Stéphanois57 Voir le message
    Le problème en faisant ça, c'est que si les 2 nombres n'ont pas la même taille il y un a.Chiffres_sign[i] ou b.Chiffres_sign[i] qui n'existe pas.
    En effet. Pour un même indice 'i', le contenu de "a.Chiffres_sign[i]" et de "b.Chiffres_sign[i]" peuvent très bien être de rangs différents, ce qui faussera le calcul. Tu auras ce problème pour les autres opérations, d'ailleurs.

    A mon avis, la solution la plus élégante pour s'en sortir est d'inverser l'ordre dans lequel tu stockes les chiffres dans "Chiffres_sign[]". Ainsi, tu auras toujours le chiffre des unités dans "Chiffres_sign[0]", le chiffre des dizaines dans "Chiffres_sign[1]", et ainsi de suite. Et tu pars sur la base du premier code qui tu as posté pour faire l'addition.

  8. #8
    Membre Expert Avatar de jopopmk
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2011
    Messages
    1 856
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

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

    Informations forums :
    Inscription : Mars 2011
    Messages : 1 856
    Par défaut
    Salut,

    ta structure est-elle une contrainte ? Sinon tu pourrais utiliser une chaîne de caractères comme tableau. Avantages :
    - prends moins de place en mémoire,
    - taille variable non limitée (cf. ta question sur la "retenue finale"),
    - parcours facilité grâce au null de fin (cf. ta question sur les longeurs des entiers),
    - directement sérialisable/affichable.

    A noter que tu peux pousser un peu plus le principe et essayer de faire fonctionner ton code pour des réels en "fixed point style".

    Bon dev.

  9. #9
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut
    Ah oui donc il faudrait que je fasse une structure qui inverse l'ordre de mon nombre ? Et la procédure deviendrait ensuite quelque chose du genre :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
     
    void Addition (Entier_long a, Entier_long b)
    {
     
    Inverse (a,b)
    **Le style de programme que j'ai posté précédemment **
    Inverse(somme)
    }
    C'est bien ça dans l'esprit ?

    Mais en faisant ca, admettons que mon nombre a ait une taille de 2 chiffres et mon nombre b de 4 chiffres.
    Exemple : 12 + 5734
    En inversant, mes deux première cases de 12 vont être vides, est-ce que le compilateur va arriver à comprendre 4+rien ?
    Je sais pas si je suis très clair.

    Oui concernant la structure c'est une contrainte... je suis obligé de faire avec.

  10. #10
    Membre Expert

    Homme Profil pro
    Responsable des études
    Inscrit en
    Mars 2009
    Messages
    553
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Responsable des études
    Secteur : Industrie

    Informations forums :
    Inscription : Mars 2009
    Messages : 553
    Par défaut
    J'ai essayé de synthétiser ce que tu dois obtenir dans le schéma ci-dessous:
    Nom : WP_20160314_001[1].jpg
Affichages : 264
Taille : 1,31 Mo

  11. #11
    Membre Expert Avatar de jopopmk
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2011
    Messages
    1 856
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

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

    Informations forums :
    Inscription : Mars 2011
    Messages : 1 856
    Par défaut
    Dommage, voilà à quoi peut ressembler une addition de deux entiers naturels en utilisant des chaînes de caractères :
    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
    char* add(char *val1, char *val2) {
    	int len1 = strlen(val1),
    		len2 = strlen(val2),
    		rest = 0;
    	char *result = malloc(((len1 > len2 ? len1 : len2) +2)*sizeof(char)),
    		 *cur1 = val1 +len1 -1,
    		 *cur2 = val2 +len2 -1,
    		 *curr = result;
    	while (cur1 >= val1 || cur2 >= val2) {
    		int dig1 = (cur1 < val1) ? 0 : *cur1-- -'0',
    			dig2 = (cur2 < val2) ? 0 : *cur2-- -'0',
    			vadd = dig1 +dig2 +rest;
    		*curr++ = (vadd %10) +'0';
    		rest = vadd /10;
    	}
    	if (rest) *curr++ = rest +'0';
    	*curr = 0;
    	strrev(result);
    	return result;
    }
    20 lignes pile et c'est torché.
    Pour gérer les entiers relatifs il faudra écrire la fonction de soustraction.

  12. #12
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut
    D'accord, franchement merci beaucoup !

    Je vais essayer de faire ça maintenant.

    Je viens de faire une procédure d'inversement :
    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
     
    void InverserTableau(Entier_long a)
    {
        int i1=0;
        int i2=a.taille;
        int x;
        while(i1<i2)
        {
            x=a.Chiffres_sign[i1];
            a.Chiffres_sign[i1]=a.Chiffres_sign[i2];
            a.Chiffres_sign[i2]=x;
            i1=i1+1;
            i2=i2-1;
        }
    }
    donc dans le programme principal j'appelle InverserTableau(a)
    et ensuite je fais un affichage pour voir si ça inverse bien :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    for (i=0; i<a.taille ;i++)
        {
            printf("%d", a.Chiffres_sign[i]);
        }
    mais ça n'affiche rien, ca me souligne la 1ère ligne du "for" et dit : Thread 1: Breakpoint 1.1

    J'ai fait une erreur dans la procédure d'inversement ?

  13. #13
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut
    Bon, j'ai un peu touché à tout, et je n'ai plus le problème du breakpoint. Mais ça ne m'inverse pas mon nombre. Pourtant j'ai refait sur papier, et il me semble que c'est la bonne méthode que j'ai appliqué. Il y a peut-être un problème dans les variables que j'ai utilisé alors ?

  14. #14
    Membre Expert

    Homme Profil pro
    Responsable des études
    Inscrit en
    Mars 2009
    Messages
    553
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Responsable des études
    Secteur : Industrie

    Informations forums :
    Inscription : Mars 2009
    Messages : 553
    Par défaut
    A priori, je dirais ici:

    Attention: pour un tableau de taille N, les index valides vont de 0 à N-1

  15. #15
    Membre Expert Avatar de jopopmk
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2011
    Messages
    1 856
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

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

    Informations forums :
    Inscription : Mars 2011
    Messages : 1 856
    Par défaut
    Effectivement l'index final n'est pas le bon, mais c'est pas le seul souci : le param Entier_long est passé par copie.

  16. #16
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut
    Oui effectivement ça doit être :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    int i2=a.taille-1;
    Mais ca m'affiche le nombre que je rentre, donc il ne s'inverse. Un peu comme s'il ne gardait pas en mémoire l'inversement ?

  17. #17
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut
    Rectification : oui c'est vrai jopopmk. C'est assez galère tous ces pointeurs lorsqu'on est novice...

    Avec ce code ça à l'air de marcher :

    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
     
    void InverserTableau(Entier_long *a) /* Inverse le tableau Chiffres_sign[] de Entier_long */
    {
        int i1=0;
        int i2=((*a).taille-1);
        int x;
        while(i1<i2)
        {
            x=(*a).Chiffres_sign[i1];
            (*a).Chiffres_sign[i1]=(*a).Chiffres_sign[i2];
            (*a).Chiffres_sign[i2]=x;
            i1=i1+1;
            i2=i2-1;
        }
    }
    Bien sûr, ne pas oublier les & après...

  18. #18
    Membre Expert Avatar de jopopmk
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2011
    Messages
    1 856
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

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

    Informations forums :
    Inscription : Mars 2011
    Messages : 1 856
    Par défaut
    T'as un souci avec la flèche ?

  19. #19
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut
    C'est la même chose non ?

    Mais j'ai un soucis, et je ne comprends pas.
    Quand un de mes 2 nombres est plus petit.
    Ex: 979 et 21. Le résultat de l'addition doit être 1000
    979 est stocké comme [9], [7], [9]
    21 est stocké comme [2], [1]

    On inverse
    979 devient 979
    et 21 devient 12.

    Là le problème c'est qu'il va faire
    9+2=1 retenue 1
    7+1+retenue=9
    9+rien=9
    = 199 --> on inverse et ça devient 991. Ce n'est pas le bon résultat.
    Ca c'est quand je le fais tourner à la main.

    Quand je rentre ces mêmes nombres, le résultat affiché est 00.
    Donc il y a 2 problèmes, un qui vient de l'algorithme, et un autre.

    D'un point de vue algorithmique, pour résoudre le problème, il faudrait que 21 soit stocké en [0], [2], [1], afin que lors de l'inversement, le problème soit résolu en devenant [1], [2], [0].
    Mais ça, je ne vois vraiment pas comment l'écrire...

  20. #20
    Membre confirmé
    Homme Profil pro
    Lycéen
    Inscrit en
    Avril 2015
    Messages
    224
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Lycéen

    Informations forums :
    Inscription : Avril 2015
    Messages : 224
    Par défaut
    Je viens de faire ça pour remédier à mon problème :

    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
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
     
    void Addition (Entier_long a, Entier_long b)
    {
        int taille_1=0, taille_2=0;
        int reste=0, i=0, s;
        int MaxTaille=0, MinTaille=0;
        taille_1=a.taille;
        taille_2=b.taille;
        int TailleTab=MaxTaille+1;
        int Somme[TailleTab];
     
        if(taille_1>=taille_2)
        {
            MaxTaille=taille_1;
            MinTaille=taille_2;
     
        }
        else
        {
            MaxTaille=taille_2;
            MinTaille=taille_1;
        }
        int j=0; /* Mettre des 0 devant le nb le plus petit ( en longueur ) */
        int TabInt[MaxTaille];
        if(b.taille<a.taille)
        {
            for (i=0;i<b.taille; i++)
            {
                TabInt[i]=b.Chiffres_sign[i];
            }
            for (i=0;i<(a.taille-b.taille);i++)
            {
                b.Chiffres_sign[i]=0;
            }
            for(i=i;i<a.taille;i++)
            {
                b.Chiffres_sign[i]=TabInt[j];
                j=j+1;
            }
        }
        else if (a.taille<b.taille)
            {
                for (i=0;i<a.taille; i++)
                {
                    TabInt[i]=a.Chiffres_sign[i];
                }
                for (i=0;i<(b.taille-a.taille);i++)
                {
                    a.Chiffres_sign[i]=0;
                }
                for(i=i;i<b.taille;i++)
                {
                    a.Chiffres_sign[i]=TabInt[j];
                    j=j+1;
                }
            }
     
     
        printf("b.Chiffre = ");
        for (i=0;i<MaxTaille;i++)
        {
            printf(" %d ",b.Chiffres_sign[i]);
        }
        printf("\n");
        printf("a.Chiffre = ");
        for (i=0;i<MaxTaille;i++)
        {
            printf(" %d ",a.Chiffres_sign[i]);
        }
        printf("\n");
     
     
        InverserTableau(&a);
        InverserTableau(&b);
     
        for (i=0 ; i<MaxTaille ; i++)
        {
            s=a.Chiffres_sign[i]+b.Chiffres_sign[i]+reste;
            if (s>9)
            {
                Somme[i]=s%10;
                reste=1;
            }
            else
            {
                Somme[i]=s;
                reste=0;
            }
        }
     
        /* Affichage de l'addition */
        for(i=TailleTab;i>=0;i--)
        {
            printf("%d", Somme[i]);
        }
    }
    Grâce aux affichages, on peut voir que le nombre le plus petit est complété par un ou des 0 devant. Mais il doit avoir une histoire de pointeurs, car si je lance mon programme comme ça, j'ai le même problème qu'avant, donc je pense qu'il faut ajouter des pointeurs, mais je ne sais pas où les mettre.

    PS :

    Je viens d'ajouter des pointeurs partout. Je n'ai pas de problèmes de compilation, donc je pense qu'ils sont bons.

    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
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
     
    void Addition (Entier_long *a, Entier_long *b)
    {
        int taille_1=0, taille_2=0;
        int reste=0, i=0, s;
        int MaxTaille=0, MinTaille=0;
        taille_1=a->taille;
        taille_2=b->taille;
        int TailleTab=MaxTaille+1;
        int Somme[TailleTab];
     
        if(taille_1>=taille_2)
        {
            MaxTaille=taille_1;
            MinTaille=taille_2;
     
        }
        else
        {
            MaxTaille=taille_2;
            MinTaille=taille_1;
        }
     
        int j=0;
        int TabInt[MaxTaille];
     
        if(b->taille < a->taille)
        {
            for (i=0;i<b->taille; i++)
            {
                TabInt[i]=b->Chiffres_sign[i];
            }
            for (i=0;i<(a->taille-b->taille);i++)
            {
                b->Chiffres_sign[i]=0;
            }
            for(i=i;i<a->taille;i++)
            {
                b->Chiffres_sign[i]=TabInt[j];
                j=j+1;
            }
        }
        else if (a->taille < b->taille)
            {
                for (i=0;i<a->taille; i++)
                {
                    TabInt[i]=a->Chiffres_sign[i];
                }
                for (i=0;i<(b->taille-a->taille);i++)
                {
                    a->Chiffres_sign[i]=0;
                }
                for(i=i;i<b->taille;i++)
                {
                    a->Chiffres_sign[i]=TabInt[j];
                    j=j+1;
                }
            }
     
     
        printf("b.Chiffre AVANT inversion = ");
        for (i=0;i<MaxTaille;i++)
        {
            printf(" %d ",b->Chiffres_sign[i]);
        }
        printf("\n");
        printf("a.Chiffre AVANT inversion = ");
        for (i=0;i<MaxTaille;i++)
        {
            printf(" %d ",a->Chiffres_sign[i]);
        }
        printf("\n");
     
        InverserTableau(&*a);
        InverserTableau(&*b);
     
        printf("b.Chiffre APRES inversion = ");
        for (i=0;i<MaxTaille;i++)
        {
            printf(" %d ",b->Chiffres_sign[i]);
        }
        printf("\n");
        printf("a.Chiffre APRES inversion  = ");
        for (i=0;i<MaxTaille;i++)
        {
            printf(" %d ",a->Chiffres_sign[i]);
        }
        printf("\n");
     
        for (i=0 ; i<MaxTaille ; i++)
        {
            s=a->Chiffres_sign[i]+b->Chiffres_sign[i]+reste;
            if (s>9)
            {
                Somme[i]=s%10;
                reste=1;
            }
            else
            {
                Somme[i]=s;
                reste=0;
            }
        }
     
        /* Affichage de l'addition */
        for(i=TailleTab;i>=0;i--)
        {
            printf("%d", Somme[i]);
        }
        printf("\n");
    }
    Cependant le résultat n'est toujours pas bon, n'y aurait-il pas un problème de pointeur avec le x par hasard dans cette procédure ? Car je me suis aperçu que ca n'inverse pas, ou mal, le nombre où les 0 ont été ajouté. L'autre nombre s'inverse très bien.

    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
     
    void InverserTableau(Entier_long *a) /* Inverse le tableau Chiffres_sign[] de Entier_long */
    {
        int i1=0;
        int i2=((*a).taille-1);
        int x;
        while(i1<i2)
        {
            x=(*a).Chiffres_sign[i1];
            (*a).Chiffres_sign[i1]=(*a).Chiffres_sign[i2];
            (*a).Chiffres_sign[i2]=x;
            i1=i1+1;
            i2=i2-1;
        }
    }

+ Répondre à la discussion
Cette discussion est résolue.
Page 1 sur 2 12 DernièreDernière

Discussions similaires

  1. [TPW] Calculatrice effectuant des opérations sur les entiers longs
    Par forum dans le forum Codes sources à télécharger
    Réponses: 0
    Dernier message: 04/12/2011, 11h36
  2. Réponses: 0
    Dernier message: 04/12/2011, 11h29
  3. opération "et" de boole sur des entiers
    Par Crapuleux_Crapaud dans le forum Général Python
    Réponses: 2
    Dernier message: 17/06/2010, 23h06
  4. Addition sur des floats
    Par Invité dans le forum C
    Réponses: 9
    Dernier message: 26/02/2010, 06h55
  5. [DB2] LIKE sur des entiers
    Par heloise dans le forum DB2
    Réponses: 1
    Dernier message: 07/10/2004, 23h30

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