Twitter iPhone pliant OnePlus 11 PS5 Disney+ Orange Livebox Windows 11

Je cale. Help !

20 réponses
Avatar
Pierre Maurette
Bonjour,

Je tourne en rond depuis deux heures sur un problème qui doit être
évident. Code réduit qui plante (exception à l'exécution):

#include <stdio.h>
#include <stdbool.h>
#include <limits.h>

/*
#if !defined(__STDC__)
#error Standard ANSI C compiler required
#endif
*/


#if defined(__cplusplus)
#error C++ compiler not allowed
#endif

typedef struct
{
int serial;
int data;
unsigned long* ul;
}
coin;

unsigned long MoyenneCoins(coin* Debut, size_t nbr)
{
size_t indice;
unsigned long result = 0, dummy;
bool overflow = false;
for(indice = 0; !overflow && (indice < nbr); indice++)
{
dummy = result;
result += *((Debut + indice)->ul);
overflow = (result < dummy);
}
overflow = overflow && (result > ULONG_MAX / nbr);
puts(overflow ? "Overflow" : "OK");
return overflow ? ULONG_MAX : result / nbr;
}

#define TAILLE 4
int main()
{
coin tabCoin[TAILLE];
unsigned long testValue = UCHAR_MAX;
tabCoin[1].ul = &testValue;
tabCoin[2] = tabCoin[1];
tabCoin[3] = tabCoin[2];
printf("%lu\n", MoyenneCoins(tabCoin, TAILLE));
return 0;
}


Merci de m'aider...

--
Pierre Maurette

10 réponses

1 2
Avatar
Stéphane Goujet
typedef struct
{
int serial;
int data;
unsigned long* ul;
}
coin;
unsigned long MoyenneCoins(coin* Debut, size_t nbr)
{
for(indice = 0; !overflow && (indice < nbr); indice++)
{
dummy = result;
result += *((Debut + indice)->ul);
overflow = (result < dummy);
}
#define TAILLE 4
int main()
{
coin tabCoin[TAILLE];
unsigned long testValue = UCHAR_MAX;
tabCoin[1].ul = &testValue;
tabCoin[2] = tabCoin[1];
tabCoin[3] = tabCoin[2];
printf("%lun", MoyenneCoins(tabCoin, TAILLE));


tabCoin[0] n'est pas initialisé ?

A+,
Stéphane.

Avatar
Pierre Maurette
typedef struct
{
int serial;
int data;
unsigned long* ul;
}
coin;
unsigned long MoyenneCoins(coin* Debut, size_t nbr)
{
for(indice = 0; !overflow && (indice < nbr); indice++)
{
dummy = result;
result += *((Debut + indice)->ul);
overflow = (result < dummy);
}
#define TAILLE 4
int main()
{
coin tabCoin[TAILLE];
unsigned long testValue = UCHAR_MAX;
tabCoin[1].ul = &testValue;
tabCoin[2] = tabCoin[1];
tabCoin[3] = tabCoin[2];
printf("%lun", MoyenneCoins(tabCoin, TAILLE));


tabCoin[0] n'est pas initialisé ?


Damned, mais c'est bien sûr ! Il manque ul dans un coin... ;-)

Merci.

--
Pierre Maurette


Avatar
Stéphane Goujet

Il manque ul dans un coin... ;-)


Ne me dites pas que vous avez écrit tout ce programme pour pouvoir
faire cette blague ? Non... Si ? Si ! Ah, l'affreux ! ;->

A+,
Stéphane.

Avatar
Jean-Marc Bourguet
Pierre Maurette writes:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif


Quel est l'objectif? Ça n'a un interet que si on a identifie l'utilisation
d'une difference de comportement entre le C et le C++ et qu'on l'indique.
Sinon, le seul effet est d'em... le pauvre type qui va devoir se tapper
l'ecriture d'un script pour pour virer ces lignes-la de tous les fichiers
quand il faudra compiler le code avec un compilateur C++. Murphy va
naturellement frapper et l'utilisation de ce script va faire manquer le
fichier unique ou la precaution etait necessaire et documentee.

A+

--
Jean-Marc

Avatar
Pierre Maurette
Pierre Maurette writes:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif


Quel est l'objectif? Ça n'a un interet que si on a identifie l'utilisation
d'une difference de comportement entre le C et le C++ et qu'on l'indique.
Sinon, le seul effet est d'em... le pauvre type qui va devoir se tapper
l'ecriture d'un script pour pour virer ces lignes-la de tous les fichiers
quand il faudra compiler le code avec un compilateur C++. Murphy va
naturellement frapper et l'utilisation de ce script va faire manquer le
fichier unique ou la precaution etait necessaire et documentee.


Je comprends que vous citiez Murphy, spécialiste de l'emmerdement
maximum.
Vous écrivez un film sur la destination d'un bout de code. Il s'agit
d'un modèle me servant à faire des tests, par exemple lors de la
fréquentation de fr.comp.lang.c, mais pas uniquement. J'utilise
Code::Blocks ou PSPad, et j'ai paramétré sous Windows une douzaine de
compilateurs, et ne les maîtrise pas tous. Il est important que je
puisse bricoler les options de construction, et il m'est arrivé,
rarement quand même, de compiler en C++ s'en m'en rendre compte, alors
que je voulais justement vérifier tel ou tel point de détail, tel ou
tel warning. Alors j'en ai eu marre de taper un retour de malloc() non
casté ou une autre entourloupe pour lever le doute.
Et là, j'ai tout copié collé, le but étant, vous avez dû vous en rendre
compte, de noyer le poisson.
J'ajoute que le plus souvent et sauf raison particulière j'écris mon
code "utile", même "plain C", en C++, et que je sais que c'est mal.

--
Pierre Maurette


Avatar
Jean-Marc Bourguet
Pierre Maurette writes:

Pierre Maurette writes:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif


Quel est l'objectif? Ça n'a un interet que si on a identifie l'utilisation
d'une difference de comportement entre le C et le C++ et qu'on l'indique.
Sinon, le seul effet est d'em... le pauvre type qui va devoir se tapper
l'ecriture d'un script pour pour virer ces lignes-la de tous les fichiers
quand il faudra compiler le code avec un compilateur C++. Murphy va
naturellement frapper et l'utilisation de ce script va faire manquer le
fichier unique ou la precaution etait necessaire et documentee.


Je comprends que vous citiez Murphy, spécialiste de l'emmerdement maximum.
Vous écrivez un film sur la destination d'un bout de code. Il s'agit d'un
modèle me servant à faire des tests,


S'assurer que des tests de particularites de C sont bien compilee avec un
compilateur C est une raison parfaitement valable chez moi.

J'ajoute que le plus souvent et sauf raison particulière j'écris mon code
"utile", même "plain C", en C++, et que je sais que c'est mal.


Ecrire du code qui reste consciemment dans l'intersection du C et du C++ me
semble etre une contrainte raisonnable.

--
Jean-Marc



Avatar
Thierry Chappuis

Pierre Maurette writes:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif


Quel est l'objectif? Ça n'a un interet que si on a identifie l'utilisa tion
d'une difference de comportement entre le C et le C++ et qu'on l'indique.
Sinon, le seul effet est d'em... le pauvre type qui va devoir se tapper
l'ecriture d'un script pour pour virer ces lignes-la de tous les fichiers
quand il faudra compiler le code avec un compilateur C++. Murphy va
naturellement frapper et l'utilisation de ce script va faire manquer le
fichier unique ou la precaution etait necessaire et documentee.

A+

--
Jean-Marc


<NEWBY>
<HS>
Comment je fais si je désire utiliser du code écrit en C dans un
projet C++, et que j'ai pas mal d'appels à malloc (c'est finalement
relativement courant)? Dois-je caster malloc pour être certain que mon
code compile avec un compilateur C++ ou alors forcer la compilation
avec un compilo C avec:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif

L'article suivant http://www.cpax.org.uk/prg/writings/casting.php
explique qu'il faut éviter de compiler du code C avec un compilateur
C++. Votre commentaire à ce sujet m'intéresse!
</HS>
</NEWBY>

Thierry


Avatar
Pascal Bourguignon
"Thierry Chappuis" writes:


Pierre Maurette writes:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif


Quel est l'objectif? Ça n'a un interet que si on a identifie l'utilisation
d'une difference de comportement entre le C et le C++ et qu'on l'indique.
Sinon, le seul effet est d'em... le pauvre type qui va devoir se tapper
l'ecriture d'un script pour pour virer ces lignes-la de tous les fichiers
quand il faudra compiler le code avec un compilateur C++. Murphy va
naturellement frapper et l'utilisation de ce script va faire manquer le
fichier unique ou la precaution etait necessaire et documentee.

A+

--
Jean-Marc


<NEWBY>
<HS>
Comment je fais si je désire utiliser du code écrit en C dans un
projet C++, et que j'ai pas mal d'appels à malloc (c'est finalement
relativement courant)? Dois-je caster malloc pour être certain que mon
code compile avec un compilateur C++ ou alors forcer la compilation
avec un compilo C avec:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif

L'article suivant http://www.cpax.org.uk/prg/writings/casting.php
explique qu'il faut éviter de compiler du code C avec un compilateur
C++. Votre commentaire à ce sujet m'intéresse!
</HS>
</NEWBY>


Le plus simple, c'est de compiler avec un compilateur C,
et de mettre dans chaque header C:

#ifdef __cplusplus
extern "C"{
#endif

...

#ifdef __cplusplus
}
#endif


--
__Pascal Bourguignon__ http://www.informatimago.com/
The rule for today:
Touch my tail, I shred your hand.
New rule tomorrow.



Avatar
Thierry Chappuis

"Thierry Chappuis" writes:


Pierre Maurette writes:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif


Quel est l'objectif? Ça n'a un interet que si on a identifie l'util isation
d'une difference de comportement entre le C et le C++ et qu'on l'indiq ue.
Sinon, le seul effet est d'em... le pauvre type qui va devoir se tapper
l'ecriture d'un script pour pour virer ces lignes-la de tous les fichi ers
quand il faudra compiler le code avec un compilateur C++. Murphy va
naturellement frapper et l'utilisation de ce script va faire manquer le
fichier unique ou la precaution etait necessaire et documentee.

A+

--
Jean-Marc


<NEWBY>
<HS>
Comment je fais si je désire utiliser du code écrit en C dans un
projet C++, et que j'ai pas mal d'appels à malloc (c'est finalement
relativement courant)? Dois-je caster malloc pour être certain que mon
code compile avec un compilateur C++ ou alors forcer la compilation
avec un compilo C avec:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif

L'article suivant http://www.cpax.org.uk/prg/writings/casting.php
explique qu'il faut éviter de compiler du code C avec un compilateur
C++. Votre commentaire à ce sujet m'intéresse!
</HS>
</NEWBY>


Le plus simple, c'est de compiler avec un compilateur C,
et de mettre dans chaque header C:

#ifdef __cplusplus
extern "C"{
#endif

...

#ifdef __cplusplus
}
#endif



Dans ce cas, le code suivant, placé dans le fichier d'implantation .c
ne pose aucun problème, sauf de s'assurer que le fichier en question
sera bien compilé avec un compilateur C.

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif

Donc, je ne comprend pas la remarque de Jean-Marc Bourguet.

Thierry




Avatar
Pierre Maurette
[...]
Comment je fais si je désire utiliser du code écrit en C dans un
projet C++, et que j'ai pas mal d'appels à malloc (c'est finalement
relativement courant)? Dois-je caster malloc pour être certain que mon
code compile avec un compilateur C++ ou alors forcer la compilation
avec un compilo C avec:

#if defined(__cplusplus)
#error C++ compiler not allowed
#endif


Notez accessoirement que ces trois lignes ne changeront rien si vous
avez effectivement des malloc() non castés ;-)

L'article suivant http://www.cpax.org.uk/prg/writings/casting.php
explique qu'il faut éviter de compiler du code C avec un compilateur
C++. Votre commentaire à ce sujet m'intéresse!


Vous avez des renseignements ici:
<URL:http://jlecomte.ifrance.com/c++/c++-faq-lite/mixing-c-and-cpp-fr.html>

Ensuite, à vous de choisir une stratégie. Sous réserve, puisque je n'ai
pas d'expérience de travail partagé, il me semble qu'un jeu de
fonctions en C (ou autre langage d'ailleurs) validées devra simplement
être lié au projet C++. Ainsi, leur maintenance reste centralisée, et
vous ne gérez pas vos fonctions globales dans le projet C++. C'est ce
qui se passe avec les API Windows.
Ensuite, il y a le copié-collé de code C dans des méthodes C++. Ça
m'arrive assez fréquemment, à partir soit de code personnel, soit de
code glané sur la toile, soit souvent d'exemples (MSDN pour ne pas le
citer). Là, il y a ce que je voudrais faire et ce que malheureusement
ce que je fais trop souvent.
Le code originalement C va compiler en C++, au prix de quelques
précautions comme le cast des malloc(). Mais il va casser certaines
règles de style fortes de C++. Déjà le malloc(), et son cast "à la C"
qui n'arrange rien. Ça va devenir nauséabond si vous free-ez des
pointeurs obtenus par new, ou si vous delete-ez d'autre obtenus par
malloc(). Donc, un peu de refactoring s'impose. A ce moment-là, autant
ne pas caster les malloc() et/ou ne pas faire le #include qui va bien.
Notez que le realloc() ne peut pas se C++-iser de façon triviale.
Sur le malloc() je suis assez strict. En revanche les trucs du MSDN, je
les copie-colle gaillardement. A une époque, je changeais puérilement
les noms, ce qui est extrêmement couillon si on y réfléchit deux
secondes.

--
Pierre Maurette

1 2