Forum |  HardWare.fr | News | Articles | PC | S'identifier | S'inscrire | Shop Recherche
1290 connectés 

  FORUM HardWare.fr
  Programmation
  C++

  try - catch en C++

 


 Mot :   Pseudo :  
 
 Page :   1  2
Page Précédente
Auteur Sujet :

try - catch en C++

n°1075382
Xixor
Posté le 08-05-2005 à 10:51:27  profilanswer
 

Bonjour,
 
je débute un peu avec le C++ et je me demandais si il était possible de faire de la gestion d'erreur en try-catch qui reprenne l'éxecution du code après le throw, et pas après le bloc catch.
 
Exemple :
 
Le but serait ici que le bloc catch n'affiche qu'un message d'avertissement si erreur.code est 0 et que l'exécution continue normalement, et qu'il quitte le programme si erreur.code vaut 1.
 
Code :
 

Citation :


....
 
struct Erreur
{
        string message;
        int code;
};
 
....
string compresse(const string& data, char flag) throw (Erreur)
{
                ......
                                        if (data2[i]=='a')
                                        {
                                                Erreur er1;
                                                er1.message ="avertissement";
                                                er1.code =0;
                                                throw er1;
                                        }
                          .....
                  return data2;
}
 
string decompresse(const string& rledata, char flag) throw (Erreur)
{
   ....
                        if (rledata2[i+1]==flag)
                        {
                                Erreur er2;
                                er2.message="erreur : flag apres flag";
                                er2.code=1;
                                throw er2;
                        }
        .....  
        return rledata2;
}
 
                                 
int main()
{
       ....
        try
        {
                string str2(compresse(str1,'#'));
                // le programme doit s'exécuter jusqu'ici, même si compresse lève une exception
                ....
                string str3(decompresse(str2,'#'));
                // mais plus là (si decompresse lève une exception)
        }
        catch (Erreur erreur)
        {
                if (erreur.code==0)
                {
                        cout <<erreur.message<<endl;
                        // LA JUSTE UN AVERTISSEMENT
                }
                else
                {
                        cout <<erreur.message<<endl;
                        return 0; // pour quitter le programme
                         
                }
        }
}


 
Voilà merci d'avance pour vos réponses et bon dimanche!
 
A+

mood
Publicité
Posté le 08-05-2005 à 10:51:27  profilanswer
 

n°1075383
Taz
bisounours-codeur
Posté le 08-05-2005 à 10:59:54  profilanswer
 

déjà, ta classe d'exception, tu là fais hérité de quelque chose dans <stdexcep>
 
ensuite, tu attrapes l'exception par &
 
et ne déclare pas le type d'exception lancé
 
pour finir : n'inclue pas de code, contente toi de définir différentes classes d'exception

n°1075412
Taz
bisounours-codeur
Posté le 08-05-2005 à 11:52:29  profilanswer
 

Code :
  1. #include <stdexcept>
  2. #include <string>
  3. namespace Xixor
  4. {
  5.   class ErreurCompression : public std::runtime_error
  6.   {
  7.   public:
  8.     explicit ErreurCompression(const std::string& );
  9.   };
  10.   class ErreurDecompression : public std::runtime_error
  11.   {
  12.   public:
  13.     explicit ErreurDecompression(const std::string& );
  14.   };
  15.   std::string compresse(const std::string& );
  16.   std::string decompresse(const std::string& );
  17. }
  18. namespace Xixor
  19. {
  20.   ErreurCompression::ErreurCompression(const std::string& msg)
  21.     : std::runtime_error(msg)
  22.   { }
  23.   ErreurDecompression::ErreurDecompression(const std::string& msg)
  24.     : std::runtime_error(msg)
  25.   { }
  26.   std::string compresse(const std::string& s)
  27.   {
  28.     if(s.empty())
  29.       throw ErreurCompression("La chaîne est vide" );
  30.     return "blah";
  31.   }
  32.   std::string decompresse(const std::string& s)
  33.   {
  34.     if(s.empty())
  35.       throw ErreurDecompression("La chaîne est vide" );
  36.     return "blih";
  37.   }
  38. }
  39. #include <iostream>
  40. int main()
  41. {
  42.   try
  43.     {
  44.       Xixor::compresse("foo" );
  45.       Xixor::compresse("" );
  46.     }
  47.   catch(const Xixor::ErreurCompression& ex)
  48.     {
  49.       std::cerr << "Une erreur s'est produite lors de la compression : "
  50.  << ex.what() << '\n';
  51.     }
  52.   try
  53.     {
  54.       Xixor::compresse("foo" );
  55.       Xixor::decompresse("" );
  56.     }
  57.   catch(const Xixor::ErreurDecompression& ex)
  58.     {
  59.       std::cerr << "Une erreur s'est produite lors de la decompression : "
  60.  << ex.what() << '\n';
  61.     }
  62.   catch(const Xixor::ErreurCompression& ex)
  63.     {
  64.       std::cerr << "Une erreur s'est produite lors de la compression : "
  65.  << ex.what() << '\n';
  66.     }
  67.   try
  68.     {
  69.       Xixor::compresse("foo" );
  70.       Xixor::decompresse("" );
  71.     }
  72.   catch(const std::exception& ex)
  73.     {
  74.       std::cerr << "Une erreur s'est produite : "
  75.  << ex.what() << '\n';
  76.     }
  77. }

pour bien faire


Message édité par Taz le 08-05-2005 à 22:17:41
n°1075500
Xixor
Posté le 08-05-2005 à 13:57:49  profilanswer
 

OK merci!
 
Je regarderai tout ça en détail ce soir !

n°1075771
chrisbk
-
Posté le 08-05-2005 à 22:06:04  profilanswer
 

Citation :

 catch(Xixor::ErreurCompression& ex)


 
pas de const ? [:le kneu]


---------------
NP: HTTP Error 764 Stupid coder found
n°1075779
Taz
bisounours-codeur
Posté le 08-05-2005 à 22:17:08  profilanswer
 

si tu en veux ...
mais pour rendre ça drôle, je devrais jeter des exceptions à base de pointeurs :D

n°1075783
Taz
bisounours-codeur
Posté le 08-05-2005 à 22:23:18  profilanswer
 

en fait, note que comme l'objet de l'exception est en ta possession, tu peux t'en servir comme tu veux. Par exemple, faire
 
ex.message = "Meilleur message de diagnostique";
throw;
 
ce que tu t'interdis avec le const.

n°1075789
Taz
bisounours-codeur
Posté le 08-05-2005 à 22:31:19  profilanswer
 

mais je te sens joueur ce soir : comment ferais-tu pour centraliser la gestion des exceptions, pour ne pas à avoir à taper plusieurs fois toutes la même série de bloc catch ?

n°1075823
chrisbk
-
Posté le 09-05-2005 à 00:18:13  profilanswer
 

A la demande express de mon grand ami push qui me rapelle fort justement et avec le tact qui lui est coutumier que j'ai posté ici [:god]
 

Taz a écrit :

mais je te sens joueur ce soir


 
ah mais pas du tout, il ne fallait pas prendre ma question comme etant un défi mais plutot comme l'expression de ma surprise, etant donné que je t'ai souvent vu brandir bien haut l'etendart du "const machin &" dans la gestion d'exception
 
 

Citation :

comment ferais-tu pour centraliser la gestion des exceptions, pour ne pas à avoir à taper plusieurs fois toutes la même série de bloc catch ?


 
votre question ne m'est pas tres claire mon cher [:klem3i1] et depuis 6 mois que je fais du C de bagnard, les exceptions, hein, je vais finir par meme pu trop de quoi il en retourne


Message édité par chrisbk le 09-05-2005 à 00:18:29

---------------
NP: HTTP Error 764 Stupid coder found
n°1075826
Taz
bisounours-codeur
Posté le 09-05-2005 à 00:41:27  profilanswer
 

comment tu ferais pour factoriser le traitement d'erreur ? dans l'exemple, j'ai deux try, et à chaque fois, plusieurs catch. Et ça fait plein de code en double pour traiter l'exception.

mood
Publicité
Posté le 09-05-2005 à 00:41:27  profilanswer
 

n°1075831
chrisbk
-
Posté le 09-05-2005 à 01:09:12  profilanswer
 

bah jbricolerais un truc a base de fonctions, vu que la seule chose qui change c'est le block try. M'enfin ne me fait pas trop passer pour un con trop longtemps et donne nous ta fine reponse [:god]


---------------
NP: HTTP Error 764 Stupid coder found
n°1075833
Taz
bisounours-codeur
Posté le 09-05-2005 à 01:12:37  profilanswer
 

Code :
  1. void gestion_erreur(const char* file, int line, const std::string& msg)
  2.   {
  3.     try
  4.       {
  5.         throw;
  6.       }
  7.     catch(Xixor::ErreurDecompression& ex)
  8.       {
  9.         std::cerr << file << ':' << line
  10.                   << " Une erreur s'est produite lors de la compression : "
  11.                   << '(' << ex.what() << " ). "
  12.                   << msg << '\n';
  13.       }
  14.     catch(Xixor::ErreurCompression& ex)
  15.       {
  16.         std::cerr << file << ':' << line
  17.                   << " Une erreur s'est produite lors de la decompression : "
  18.                   << '(' << ex.what() << " ). "
  19.                   << msg << '\n';
  20.       }
  21.   }
  22. #define GESTION_ERREUR(MSG) Xixor::gestion_erreur(__FILE__, __LINE__, MSG)


 

Code :
  1. try
  2.     {
  3.       Xixor::compresse("foo" );
  4.       Xixor::decompresse("" );
  5.     }
  6.   catch(...)
  7.     {
  8.       GESTION_ERREUR("Ça suffit maintenant !" );
  9.     }


 
et hop, un répartisseur d'exception, sans dynamic_cast :)

n°1075836
chrisbk
-
Posté le 09-05-2005 à 01:18:35  profilanswer
 

moué [:ohtusais]


---------------
NP: HTTP Error 764 Stupid coder found
n°1075841
Taz
bisounours-codeur
Posté le 09-05-2005 à 01:35:53  profilanswer
 

fais des cauchemards !

n°1076016
++fab
victime du syndrome IH
Posté le 09-05-2005 à 11:01:13  profilanswer
 

C'est quoi ce complot hérétique nocturne contre la religion C++ ?
C'etait pour montrer à chrisbk qu'il existe aussi du C++ de bagnard ? :D

n°1076037
chrisbk
-
Posté le 09-05-2005 à 11:11:47  profilanswer
 

chui clairement pas fan de cette bidouille [:ohtusais] et la macro n'est pas la pour arranger les choses [:ohtusais]
 
fab >> du C++ de bagnard je connais, j'en ai meme fait a mes debuts [:marc] (du beau C with classes [:marc])


---------------
NP: HTTP Error 764 Stupid coder found
n°1076042
Taz
bisounours-codeur
Posté le 09-05-2005 à 11:14:04  profilanswer
 

spa une bidouille. Et la macro, elle set à pas grand chose.
 
Le dernier conseil du jour : ne jamais relancé une exception avec un 'throw e;'. Toujours utilisé 'throw;'. Sinon tu fous en l'air le polymorphisme.

n°1076059
++fab
victime du syndrome IH
Posté le 09-05-2005 à 11:22:42  profilanswer
 

Et à quoi te sert le polymorphisme dans ta bidouille ? [:itm] Et à quoi ça te sert de faire hériter tes classes d'exceptions de std::exception (ou une de ces filles) ? [:itm]
Sans compter que la moindre modification dans le bloc try ou dans le nom des classes d'exceptions t'oblige à tout recoder ...
 

n°1076065
Taz
bisounours-codeur
Posté le 09-05-2005 à 11:26:26  profilanswer
 

...
 
réfléchi d'abord à mon message précédent. En quoi
 

Code :
  1. catch(My::Exception& e)
  2. {
  3.   e.add_info("shit can happen" );
  4.   throw e;
  5. }


 
est un bug alors que
 

Code :
  1. catch(My::Exception& e)
  2. {
  3.   e.add_info("shit can happen" );
  4.   throw;
  5. }


 
est correcte ?

n°1076068
++fab
victime du syndrome IH
Posté le 09-05-2005 à 11:27:59  profilanswer
 

OK pour ça ...

n°1076076
Taz
bisounours-codeur
Posté le 09-05-2005 à 11:31:05  profilanswer
 

pourquoi ?

n°1076081
chrisbk
-
Posté le 09-05-2005 à 11:33:53  profilanswer
 

++fab a écrit :

Et à quoi te sert le polymorphisme dans ta bidouille ? [:itm] Et à quoi ça te sert de faire hériter tes classes d'exceptions de std::exception (ou une de ces filles) ? [:itm]
Sans compter que la moindre modification dans le bloc try ou dans le nom des classes d'exceptions t'oblige à tout recoder ...


 
 
cet argument m'a l'air quand meme sacrement foireux [:marc]


---------------
NP: HTTP Error 764 Stupid coder found
n°1076084
++fab
victime du syndrome IH
Posté le 09-05-2005 à 11:34:48  profilanswer
 

ma remarque à 11h22 n'etait pas du tout destiné à ton dernier conseil du jour, mais à ta bidouille.
Qu'est ce que ça apporte par rapport à ce que tu avais écrit plus haut ? (en bien)
# try
#     {
#       Xixor::compresse("foo" );
#       Xixor::decompresse("" );
#     }
#   catch(const std::exception& ex)
#     {
#       std::cerr << "Une erreur s'est produite : "
#         << ex.what() << '\n';
#     }

n°1076097
++fab
victime du syndrome IH
Posté le 09-05-2005 à 11:42:06  profilanswer
 

chrisbk a écrit :

cet argument m'a l'air quand meme sacrement foireux [:marc]


Le nom des classes d'exceptions, c'est qqchose que je change environ 3 ou 4 fois, mais c'est une lacune personnelle. J'ai toujours tendance à sous-estimer l'importance d'une conception tot dans le projet de la hiérarchie des classes d'exception. Malgré les conseils du BS  [:petrus75]

n°1076107
Taz
bisounours-codeur
Posté le 09-05-2005 à 11:51:46  profilanswer
 

ben tu peux centraliser ton code de gestion d'erreur. Notemment si tu dois prendre des décisions (genre ouvrir un message d'erreur). Je te dis pas qu'il faut utiliser que ça, je te dis qu'il y a de la place pour les deux.

n°1076403
Taz
bisounours-codeur
Posté le 09-05-2005 à 15:02:25  profilanswer
 

alors vous abandonnez ?
 

Code :
  1. #include <stdexcept>
  2. #include <string>
  3. #include <iostream>
  4. namespace My
  5. {
  6.   class Exception : public std::exception
  7.   {
  8.     std::string info;
  9.   public:
  10.     virtual void add_info(const std::string& info)
  11.     {
  12.       this->info += info;
  13.     }
  14.     virtual const char* what() const throw()
  15.     {
  16.       return this->info.c_str();
  17.     }
  18.     virtual ~Exception() throw() { }
  19.   };
  20.   class BadException : public Exception
  21.   {
  22.   public:
  23.     virtual ~BadException() throw() { }
  24.   };
  25. }
  26. int main()
  27. {
  28.   try
  29.     {
  30.       try
  31. {
  32.   throw My::BadException();
  33. }
  34.       catch(My::Exception& e)
  35. {
  36.   e.add_info("blah" );
  37.   throw e; // ou throw; ?
  38. }
  39.     }
  40.   catch(My::BadException& e)
  41.     {
  42.       std::cerr << "BadException " << e.what() << '\n';
  43.     }
  44.   catch(My::Exception& e)
  45.     {
  46.       std::cerr << "Exception " << e.what() << '\n';
  47.     }
  48. }

sans compiler, vous pensez que ça donne quoi ça ?

n°1076473
++fab
victime du syndrome IH
Posté le 09-05-2005 à 15:38:41  profilanswer
 

"Exception" (sans compiler)

n°1076496
Taz
bisounours-codeur
Posté le 09-05-2005 à 15:49:59  profilanswer
 

et pourquoi ?

n°1076510
skelter
Posté le 09-05-2005 à 15:54:57  profilanswer
 

parce que l'exception jetee est une My::Exception par lien polymorphique mais lorsque on fait trow e; on perd l'informartion sur le caractere dynamique du type de l'exception (pas sur :ange:, et pas sur que ca ve dire qulequechose) qui devien My::Exception

n°1076513
++fab
victime du syndrome IH
Posté le 09-05-2005 à 15:55:29  profilanswer
 

Taz a écrit :

et pourquoi ?


 
throw; ça propage l'exception.
 
throw e; ça déclenche une exception du type statique de e. e construit par [edit]COPY[\edit]  constructor.


Message édité par ++fab le 09-05-2005 à 16:11:48
n°1076516
++fab
victime du syndrome IH
Posté le 09-05-2005 à 15:56:37  profilanswer
 

throw; préserve le type dynamique de e.

n°1076521
Taz
bisounours-codeur
Posté le 09-05-2005 à 15:58:37  profilanswer
 

bon ça va. la clef étant 'type statique'.

n°1076537
++fab
victime du syndrome IH
Posté le 09-05-2005 à 16:05:40  profilanswer
 

plus précisément, lors d'un throw My::badException(), une copie temporaire est faite, et elle perdure tant qu'il y a un gestionnaire capable de traiter l'exception. Si l'affaire se termine par autre chose que throw; la copie temporaire est détruite et désallouée !

n°1077102
++fab
victime du syndrome IH
Posté le 09-05-2005 à 23:13:12  profilanswer
 

J'ai fini par réaliser l'objectif de ton trick. Vu qu'il était enrober de glaise, je l'ai pris tel quel et j'ai cru que tu rennonçais au polymorphisme ... d'ou ma surprise.
Ton trick sert donc à réaliser une centralisation décentrée (dans le corps d'une fonction) de la gestion des exceptions. C'est un poil obfuscant à mon gout, mais ça sépare encore plus le code d'erreur du reste.
 
On pourrait peut etre s'en servir dans un cas, sans obfuscations aucune :
 
Supposons que l'on ai 2 hiérarchies de classes d'exceptions (distinctes).
On récupère habituellement les exceptions dans le plus pur style "les enfants d'abord" (pour éviter le dynamic_cast<> ). Sauf que lorsque l'on a deux hiérarchies distinctes, c'est pas évident de rendre la gestion très lisible.
A ce moment la, Taz exception's trick :
 

Code :
  1. try{/*...*/}
  2. catch(const std::exception& e)
  3. { GESTION_ERREUR1("toto" ) }
  4. catch(const nonstd::exception& e)
  5. { GESTION_ERREUR2("toto" ) }

n°1077107
Taz
bisounours-codeur
Posté le 09-05-2005 à 23:14:55  profilanswer
 

ben à chaque fois tu écris autant de  catch ...
 
# catch(const std::exception& e)
# { GESTION_ERREUR1("toto" ) }
# catch(const nonstd::exception& e)
# { GESTION_ERREUR2("toto" ) }
 
tu duplique à chaque fois. le but c'est foutre ça dans une fonction

n°1077108
++fab
victime du syndrome IH
Posté le 09-05-2005 à 23:15:01  profilanswer
 

Et encore, c'est criticable puisqu'il faut faire 2 fonctions, qu'on va quand meme essayer de mettre dans le meme namespace.

n°1077111
++fab
victime du syndrome IH
Posté le 09-05-2005 à 23:16:14  profilanswer
 

Taz a écrit :

ben à chaque fois tu écris autant de  catch ...


ben non, je prend juste la base

n°1077114
Taz
bisounours-codeur
Posté le 09-05-2005 à 23:17:05  profilanswer
 

bah la tu perds des informations de types, et tu dois dynamic_cast'er pour en savoir plus dans tes trucs de gestions d'erreurs.

n°1077118
++fab
victime du syndrome IH
Posté le 09-05-2005 à 23:19:40  profilanswer
 

Regarde bien, y a 2 macros ... qui appelle chacune une fonction différente, mais ça n'apparait pas OK.

n°1077119
Taz
bisounours-codeur
Posté le 09-05-2005 à 23:21:27  profilanswer
 

ben alors de quoi tu parles ? c'est exactement la même chose. Je t'ai jamais dit que tu devais ne faire qu'une seule et unique fonction.

mood
Publicité
Posté le   profilanswer
 

 Page :   1  2
Page Précédente

Aller à :
Ajouter une réponse
  FORUM HardWare.fr
  Programmation
  C++

  try - catch en C++

 

Sujets relatifs
probleme de try catchComment créer une page html dans un catch
try/catch et retour de fonction[C++] while & try-catch
try catch en wxWidgets / C++JSP : Catch d'une erreur
catch (...): peut-on récupérer l'exception?[Resolu][JAVA]Problème de try catch et if else
pourquoi faut-il bannir std::exit | bloc try-catch fonctionnelRecommencer un try tant que le catch s'active
Plus de sujets relatifs à : try - catch en C++


Copyright © 1997-2022 Hardware.fr SARL (Signaler un contenu illicite / Données personnelles) / Groupe LDLC / Shop HFR