Manipulation des nombres complexes en C [Résolu/Fermé]

Signaler
-
Messages postés
26
Date d'inscription
lundi 19 juillet 2010
Statut
Membre
Dernière intervention
16 octobre 2010
-
Bonjour,

Je suis débutante en langage C et je dois mettre en place un programme écrit C, permettant de faire des calculs sur les nombres complexes.
La structure suivante est donnée:

typedef struct {
double Re;
double Im;
}
Complexe;

je dois écrire les fonctions suivantes:

1. La fonction Complexe LectureC() qui permet la saisie au clavier des parties reelles et imaginaires d'un nombre complexe.

2. la procédure void EcritureC(Complexe z) qui permet d'affaicher à l'écran un nombre complexe passé en parametre sous la forme z = Re + i Im.

3. La fonction Complexe SommeC(Complexe z1, Complexe z2) qui calcule la somme de deux passées en paramètre de la fonction , résultat r= z1+z2.

J'ai également des questions similaires pour faire multiplications, divisions, ...

Pour l'instant je n'ai fait que ces 3 questions mais mon programme ne fonctionne pas.

#include <stdio.h>
#include <stdlib.h>

typedef struct
{
double Re;
double Im;
} Complexe;

Complexe lectureC(Complexe z)
{
scanf ("%f", &z.Re);
scanf ("%f", &z.Im);
return z;
}

void EcritureC(Complexe z)
{
printf ("%f = %f + i %f\n",z, z.Re, z.Im);
}

Complexe sommeC(Complexe z1, Complexe z2)
{
Complexe r;
r.Re= z1.Re+ z2.Re;
r.Im= z1.Im+ z2.Im;
return r;
}

main ()
{
Complexe z1;
Complexe z2;
Complexe z3;

printf ("entrez un nombre réel de z1 et un nomre imaginaire z1: \n");
z1 = lectureC (z1);


printf ("entrez un reel de z2 et un imaginaire z2: \n");
z2 = lectureC (z2);


Complexe sommeC(z1,z2);
printf ("la partie reel de z3 est : %f\n", z3.Re );
printf ("la partie imaginaire de z3 est : %f \n", z3.Im);
EcritureC(z3);


return 0; }


Pouvez vous m'aider?



4 réponses

Messages postés
26
Date d'inscription
lundi 19 juillet 2010
Statut
Membre
Dernière intervention
16 octobre 2010
27
#include <stdio.h>
#include <stdlib.h>

typedef struct
{
double Re;
double Im;
} Complexe;

void lectureC(Complexe* z)
{
scanf ("%lf", &z->Re);
scanf ("%lf", &z->Im);
}

void EcritureC(Complexe z)
{
printf ("%lf + i %lf\n", z.Re, z.Im);
}

Complexe* sommeC(Complexe z1, Complexe z2)
{
Complexe* r=(Complexe*)malloc(sizeof(Complexe));
r->Re= z1.Re+ z2.Re;
r->Im= z1.Im+ z2.Im;
return r;
}

Complexe* produitC(Complexe z1, Complexe z2)
{
Complexe* r=(Complexe*)malloc(sizeof(Complexe));
r->Re= z1.Re * z2.Re - z1.Im * z2.Im;
r->Im= z1.Re * z2.Im+ z2.Re * z1.Im;
return r;
}


Complexe* divisionC(Complexe z1, Complexe z2)
{
Complexe* tmp=(Complexe*)malloc(sizeof(Complexe));
Complexe* r=NULL;
double m= z2.Im*z2.Im+z2.Re*z2.Re;
tmp->Re= z2.Re/m;
tmp->Im= -z2.Im/m;
r= produitC(z1,*tmp);
free(tmp);
return r;
}

main ()
{
Complexe z1,z2;
Complexe *z3=NULL;

printf ("entrez un nombre réel de z1 et un nomre imaginaire z1: \n");
lectureC (&z1);


printf ("entrez un reel de z2 et un imaginaire z2: \n");
lectureC (&z2);


z3 = sommeC(z1,z2);
printf ("la partie reel de z3 est : %f\n", z3->Re );
printf ("la partie imaginaire de z3 est : %f \n", z3->Im);
//somme
printf("\nz1+z2=");
EcritureC(*z3);
free(z3);
//produit
printf("\nz1*z2=");
z3=produitC(z1,z2);
EcritureC(*z3);
free(z3);
//division
printf("\nz1/z2=");
z3=divisionC(z1,z2);
EcritureC(*z3);
free(z3);
//
system("pause");
return 0;
}
9
Merci

Quelques mots de remerciements seront grandement appréciés. Ajouter un commentaire

CCM 57107 internautes nous ont dit merci ce mois-ci

Messages postés
26
Date d'inscription
lundi 19 juillet 2010
Statut
Membre
Dernière intervention
16 octobre 2010
27
nn c'est bien des %lf vu qu'on travail avec des doubles et non po des float (essai avec %f et puis avec %lf pour vérifier ;) )
pr l'allocation, c'est nécessaire et c'est pourquoi son programme ne marchait po...
Messages postés
11066
Date d'inscription
samedi 5 mai 2007
Statut
Contributeur
Dernière intervention
18 octobre 2016
1 688
Non, je confirme bien.
Avec un printf, on utilise %f pour les doubles et les float.
Par contre pour les scanf, on utilise %f pour les float et %lf pour les doubles.
Ceci est impératif pour que le code soit compliant ISO C89/90. Par contre, l'ISO C99 est plus permissif et tolère %lf dans le scanf. Mais ce n'est pas conseillé.
D'ailleurs, lis bien le man printf, tu verras bien que le %l ne s'applique pas aux floats.

De plus, pour les structures, il n'y a pas besoin d'allouer si on ne passe pas par des pointeurs comme il avait fait initialement vu que ça sera alloué dans le stack...

Cdlt,
Messages postés
26
Date d'inscription
lundi 19 juillet 2010
Statut
Membre
Dernière intervention
16 octobre 2010
27
je ne vois pas en quoi ce ne sera pas conforme vu que double = long double dans les architecture ressente..
Messages postés
11066
Date d'inscription
samedi 5 mai 2007
Statut
Contributeur
Dernière intervention
18 octobre 2016
1 688
Tu confonds plusieurs points.
conforme vu que double = long double dans les architecture ressente..
Non. Ceci est vrai à ma connaissance en Visual C++, mais ce n'est pas généralisé à l'ensemble des compilateurs. D'ailleurs, pourquoi ça le serait, ce n'est pas dit dans l'iso C99.
En plus, %lf dans un scanf ce n'est pas pour un long double, mais pour un double. Pour un long double, on utilisera %Lf.
Dans le printf, on utilisera %Lf pour le long double et %f pour le float et double.

Ensuite pourquoi, on met un %f pour un float et pour double ? Car printf est une fonction avec un nombre d'argument variable. Donc les arguments respecteront le principe de promotion. Le float sera promu en double. Ainsi %f sert pour le float et le double.
Et puis, pour t'en convaincre, je le répète, lis le man du printf. Tu ne verras pas d'allusion à ton %lf pour le double. Tu vas au paragraphe %f, et tu constateras que ça parle de double, et non de float...
Messages postés
26
Date d'inscription
lundi 19 juillet 2010
Statut
Membre
Dernière intervention
16 octobre 2010
27
oui, j'ai vu. merci pour tes clarifications =)
Messages postés
151
Date d'inscription
jeudi 17 décembre 2009
Statut
Membre
Dernière intervention
31 août 2012
8
Salut,

Tout ce que tu as écris pour l'instant fonctionne ?

Pourquoi as-tu besoin d'aide ?
le programme est bon, il n'y a pas d'erreur, mais quand je le teste, par exemple la fonction affichage donne
"0.0000=0.0000+0.0000"
au lieu de calculer et de mettre les bonnes valeurs, je pense qu'il y a un problème à cause du %f mais j'en suis pas sûr.
Messages postés
11066
Date d'inscription
samedi 5 mai 2007
Statut
Contributeur
Dernière intervention
18 octobre 2016
1 688
Bonjour,

Quelques corrections :
main () => int main (void)
Pour les scanf (scanf ("%f", &z.Re);) ce n'est pas %f mais %lf (L minuscule), sinon t'obtiendras des 0.0000

Cdlt,
Merci beaucoup!
Mais je ne comprends pas pourquoi il ne calcule pas la somme de z1+ z2, la partie réelle de z3 j'obtiens "0.000", j'ai la même chose pour la partie imaginaire et donc pour l'affichage de z3 ca donne "0.000 = 0.000+0.000".

Cordialement
Messages postés
11066
Date d'inscription
samedi 5 mai 2007
Statut
Contributeur
Dernière intervention
18 octobre 2016
1 688
Le problème de votre fonction somme est que vous créez un objet (structure) Complexe dans une fonction et vous la renvoyez. Cette dernière sera détruite.
Pour cela, soit il faut passer par une déclaration persistante (static) soit et je vous le conseille de passer trois arguments dans la fonction somme : sommeC(Complexe *z, Complexe z1, Complexe z2)
Il vous suffira de déclarer Complexe z; dans votre main, et d'appeler la fonction : sommeC(&z, z1, z2);
Et enfin, attention pour la fonction d'affichage : vous mettez printf("%f",z); ça ne va pas faire ce que vous souhaitez.
Messages postés
78
Date d'inscription
samedi 9 octobre 2010
Statut
Membre
Dernière intervention
12 décembre 2010
18
à part le fait que z3 n'est pas affecté dans la ligne Complexe SommeC.., tout parait bon.