Donc en effet et si je ne m'abuse, NDEBUG concerne bien assert
et assert seulement et aucunement une compilation en mode
debug, ni l'inverse d'ailleurs.
Même si on s'attend quand même
à trouver NDEBUG là où il n'y a pas de compilation en "mode
debug" :)
Donc en effet et si je ne m'abuse, NDEBUG concerne bien assert
et assert seulement et aucunement une compilation en mode
debug, ni l'inverse d'ailleurs.
Même si on s'attend quand même
à trouver NDEBUG là où il n'y a pas de compilation en "mode
debug" :)
Donc en effet et si je ne m'abuse, NDEBUG concerne bien assert
et assert seulement et aucunement une compilation en mode
debug, ni l'inverse d'ailleurs.
Même si on s'attend quand même
à trouver NDEBUG là où il n'y a pas de compilation en "mode
debug" :)
Donc en effet et si je ne m'abuse, NDEBUG concerne bien assert
et assert seulement et aucunement une compilation en mode
debug, ni l'inverse d'ailleurs.
La norme ne connaît pas de notion de « mode debug »
Je ne suis pas sûr ce qu'on entend par « mode debug ».
Donc en effet et si je ne m'abuse, NDEBUG concerne bien assert
et assert seulement et aucunement une compilation en mode
debug, ni l'inverse d'ailleurs.
La norme ne connaît pas de notion de « mode debug »
Je ne suis pas sûr ce qu'on entend par « mode debug ».
Donc en effet et si je ne m'abuse, NDEBUG concerne bien assert
et assert seulement et aucunement une compilation en mode
debug, ni l'inverse d'ailleurs.
La norme ne connaît pas de notion de « mode debug »
Je ne suis pas sûr ce qu'on entend par « mode debug ».
Je ne suis pas sûr ce qu'on entend par « mode debug ».
Je pense que ce sont des utilisateurs de VC++ qui ont fait
allusion au "mode debug" de celui-ci, comme ils auraient pu
faire allusion au "mode release".
Quand on bascule en "mode release", VC++ (le mien, 2005, en
tout cas) définit la macro NDEBUG.
Mais on est bien d'accord c'est un comportement par défaut de
VC++ rien de plus.
Je ne suis pas sûr ce qu'on entend par « mode debug ».
Je pense que ce sont des utilisateurs de VC++ qui ont fait
allusion au "mode debug" de celui-ci, comme ils auraient pu
faire allusion au "mode release".
Quand on bascule en "mode release", VC++ (le mien, 2005, en
tout cas) définit la macro NDEBUG.
Mais on est bien d'accord c'est un comportement par défaut de
VC++ rien de plus.
Je ne suis pas sûr ce qu'on entend par « mode debug ».
Je pense que ce sont des utilisateurs de VC++ qui ont fait
allusion au "mode debug" de celui-ci, comme ils auraient pu
faire allusion au "mode release".
Quand on bascule en "mode release", VC++ (le mien, 2005, en
tout cas) définit la macro NDEBUG.
Mais on est bien d'accord c'est un comportement par défaut de
VC++ rien de plus.
J'utilise VC++ depuis quelque semaines, et je n'y ai pas trouvé
un mode debug non plus.
Et c'est où, cette « mode release »
2005, et je ne l'ai pas trouvé.
Le comportement par défaut de VC++, c'est de ne pas définir
NDEBUG.
Il est défini dans certaines configurations proposées
par l'IDE.
(Et est-ce que tu as déjà trouvé un
défaut quelconque qui convient sans modification à ton
environement et à ta mode de travailler ?)
J'utilise VC++ depuis quelque semaines, et je n'y ai pas trouvé
un mode debug non plus.
Et c'est où, cette « mode release »
2005, et je ne l'ai pas trouvé.
Le comportement par défaut de VC++, c'est de ne pas définir
NDEBUG.
Il est défini dans certaines configurations proposées
par l'IDE.
(Et est-ce que tu as déjà trouvé un
défaut quelconque qui convient sans modification à ton
environement et à ta mode de travailler ?)
J'utilise VC++ depuis quelque semaines, et je n'y ai pas trouvé
un mode debug non plus.
Et c'est où, cette « mode release »
2005, et je ne l'ai pas trouvé.
Le comportement par défaut de VC++, c'est de ne pas définir
NDEBUG.
Il est défini dans certaines configurations proposées
par l'IDE.
(Et est-ce que tu as déjà trouvé un
défaut quelconque qui convient sans modification à ton
environement et à ta mode de travailler ?)
C'est uniquement dans le cas de la construction d'un
tableau "automatique" (i.e. alloué dans la pile) que seul l'objet levant
l'exception est détruit.
Même pas au fait.
Les objets dans le tableau construits avant la levée de l'exception
seront détruits mais pas l'objet levant l'exception. Si l'exception est
levée dans le constructeur je veux dire. Dans ce cas l'objet en question
n'est pas construit du tout.
C'est uniquement dans le cas de la construction d'un
tableau "automatique" (i.e. alloué dans la pile) que seul l'objet levant
l'exception est détruit.
Même pas au fait.
Les objets dans le tableau construits avant la levée de l'exception
seront détruits mais pas l'objet levant l'exception. Si l'exception est
levée dans le constructeur je veux dire. Dans ce cas l'objet en question
n'est pas construit du tout.
C'est uniquement dans le cas de la construction d'un
tableau "automatique" (i.e. alloué dans la pile) que seul l'objet levant
l'exception est détruit.
Même pas au fait.
Les objets dans le tableau construits avant la levée de l'exception
seront détruits mais pas l'objet levant l'exception. Si l'exception est
levée dans le constructeur je veux dire. Dans ce cas l'objet en question
n'est pas construit du tout.
Sylvain Togni wrote:Dans ce cas je teste :
1 - exécution sans gestion d'erreur (Time without errors)
2 - exécution avec exception (chaque appel lance une exception ou
presque)
3 - exécution avec gestion des exception mais sans levée d'except ion
4 - avec exception, mais peu d'exceptions sont effectivement levées
5 - erreur par valeurs de retour (pratiquement tous les appels gén ères
des erreurs)
6 - erreur par valeurs de retour (peu d'erreurs relevées)
Voici les temps que j'obtiens chez moi (compilé avec g++
avec les options par défaut):
Time without errors : 1.28000 sec
Time with exceptions : 89.0000 sec
Time with (no) exceptions : 1.31000 sec
Time with (few) exceptions : 2.03000 sec
Time with return values : 2.33000 sec
Time with (few) return values : 2.34000 sec
La bonne performance du 3 viens du test effectué (i < 0) par
rapport aux autres tests (i%10 == 0 ou i%100000 == 0).
On a chez moi (VC6) des résultats plus serrés,
malgré le paramètre supplémentaire que la solution à base de
valeurs de retour entraîne :
Time without errors : 2.64800 sec
Time with exceptions : 102.900 sec
Time with (no) exceptions : 2.75700 sec
Time with (few) exceptions : 2.75800 sec
Time with return values : 2.86700 sec
Time with (few) return values : 2.60200 sec
En effet, mais chez moi ça donne des résultats pour le moins bizarre ...
Time without errors : 2.04000 sec
Time with exceptions : 90.0000 sec
Time with (no) exceptions : 2.12000 sec <--
Time with (few) exceptions : 2.06000 sec <--
Time with return values : 2.34000 sec
Time with (few) return values : 2.35000 sec
Comment le fait de ne pas lever d'exception peut être plus
lent ? Bizarre ... bizarre ...
Bref, il faut regarder les résultats avec des pincettes
et la seule chose à retenir est :
1 - un bloc try-catch ne coûte rien (ou presque) tant qu'une
exception n'est pas levée
2 - le coût de lever d'une exception est élevé
3 - le coup d'une gestion d'erreur par valeur de retour est
indépendant du fait qu'il y ait une erreur ou non.
J'en conclu quand même que pour des *erreurs*, les exceptions
sont plus efficaces.
Après, si c'est plus un retour à traiter différemment (i.e.
qqch qui arrive fréquemment), alors une valeur de retour
s'impose.
Sylvain Togni wrote:
Dans ce cas je teste :
1 - exécution sans gestion d'erreur (Time without errors)
2 - exécution avec exception (chaque appel lance une exception ou
presque)
3 - exécution avec gestion des exception mais sans levée d'except ion
4 - avec exception, mais peu d'exceptions sont effectivement levées
5 - erreur par valeurs de retour (pratiquement tous les appels gén ères
des erreurs)
6 - erreur par valeurs de retour (peu d'erreurs relevées)
Voici les temps que j'obtiens chez moi (compilé avec g++
avec les options par défaut):
Time without errors : 1.28000 sec
Time with exceptions : 89.0000 sec
Time with (no) exceptions : 1.31000 sec
Time with (few) exceptions : 2.03000 sec
Time with return values : 2.33000 sec
Time with (few) return values : 2.34000 sec
La bonne performance du 3 viens du test effectué (i < 0) par
rapport aux autres tests (i%10 == 0 ou i%100000 == 0).
On a chez moi (VC6) des résultats plus serrés,
malgré le paramètre supplémentaire que la solution à base de
valeurs de retour entraîne :
Time without errors : 2.64800 sec
Time with exceptions : 102.900 sec
Time with (no) exceptions : 2.75700 sec
Time with (few) exceptions : 2.75800 sec
Time with return values : 2.86700 sec
Time with (few) return values : 2.60200 sec
En effet, mais chez moi ça donne des résultats pour le moins bizarre ...
Time without errors : 2.04000 sec
Time with exceptions : 90.0000 sec
Time with (no) exceptions : 2.12000 sec <--
Time with (few) exceptions : 2.06000 sec <--
Time with return values : 2.34000 sec
Time with (few) return values : 2.35000 sec
Comment le fait de ne pas lever d'exception peut être plus
lent ? Bizarre ... bizarre ...
Bref, il faut regarder les résultats avec des pincettes
et la seule chose à retenir est :
1 - un bloc try-catch ne coûte rien (ou presque) tant qu'une
exception n'est pas levée
2 - le coût de lever d'une exception est élevé
3 - le coup d'une gestion d'erreur par valeur de retour est
indépendant du fait qu'il y ait une erreur ou non.
J'en conclu quand même que pour des *erreurs*, les exceptions
sont plus efficaces.
Après, si c'est plus un retour à traiter différemment (i.e.
qqch qui arrive fréquemment), alors une valeur de retour
s'impose.
Sylvain Togni wrote:Dans ce cas je teste :
1 - exécution sans gestion d'erreur (Time without errors)
2 - exécution avec exception (chaque appel lance une exception ou
presque)
3 - exécution avec gestion des exception mais sans levée d'except ion
4 - avec exception, mais peu d'exceptions sont effectivement levées
5 - erreur par valeurs de retour (pratiquement tous les appels gén ères
des erreurs)
6 - erreur par valeurs de retour (peu d'erreurs relevées)
Voici les temps que j'obtiens chez moi (compilé avec g++
avec les options par défaut):
Time without errors : 1.28000 sec
Time with exceptions : 89.0000 sec
Time with (no) exceptions : 1.31000 sec
Time with (few) exceptions : 2.03000 sec
Time with return values : 2.33000 sec
Time with (few) return values : 2.34000 sec
La bonne performance du 3 viens du test effectué (i < 0) par
rapport aux autres tests (i%10 == 0 ou i%100000 == 0).
On a chez moi (VC6) des résultats plus serrés,
malgré le paramètre supplémentaire que la solution à base de
valeurs de retour entraîne :
Time without errors : 2.64800 sec
Time with exceptions : 102.900 sec
Time with (no) exceptions : 2.75700 sec
Time with (few) exceptions : 2.75800 sec
Time with return values : 2.86700 sec
Time with (few) return values : 2.60200 sec
En effet, mais chez moi ça donne des résultats pour le moins bizarre ...
Time without errors : 2.04000 sec
Time with exceptions : 90.0000 sec
Time with (no) exceptions : 2.12000 sec <--
Time with (few) exceptions : 2.06000 sec <--
Time with return values : 2.34000 sec
Time with (few) return values : 2.35000 sec
Comment le fait de ne pas lever d'exception peut être plus
lent ? Bizarre ... bizarre ...
Bref, il faut regarder les résultats avec des pincettes
et la seule chose à retenir est :
1 - un bloc try-catch ne coûte rien (ou presque) tant qu'une
exception n'est pas levée
2 - le coût de lever d'une exception est élevé
3 - le coup d'une gestion d'erreur par valeur de retour est
indépendant du fait qu'il y ait une erreur ou non.
J'en conclu quand même que pour des *erreurs*, les exceptions
sont plus efficaces.
Après, si c'est plus un retour à traiter différemment (i.e.
qqch qui arrive fréquemment), alors une valeur de retour
s'impose.
J'utilise VC++ depuis quelque semaines, et je n'y ai pas
trouvé un mode debug non plus.
Et comme tu l'utilises en ligne de commande, ainsi que tu l'as
dit dans un autre post, c'est normal :)
Mais tout le monde n'est pas masochiste comme toi ;) Quelle
idée de ne pas utiliser l'IDE :) Moi j'aime bien utiliser
l'IDE je trouve ça très pratique. Emacs et les makefiles j'ai
passé l'âge.
Ce "mode debug" ou "configuration debug" si tu préfères est
évidemment une cuisine de l'IDE.Et c'est où, cette « mode release »
Oh... juste à côté du "mode debug" ;)
J'utilise aussi VC++ 2005, et je ne l'ai pas trouvé.
Tu n'utilises pas VC++ Tu utilises cl 2005, i.e le compilateur
de VC++ 2005 Dans VC++ il y a V qui signifie Visual, ce que
tout le monde comprend comme l'IDE complet :-)
Le comportement par défaut de VC++, c'est de ne pas définir
NDEBUG.
Le comportement par défaut de VC++ (avec un V comme Visual,
donc, l'IDE) est bien de définir par défaut NDEBUG en "mode
relase" :)
Le compilateur, cl, lui ne définit rien du tout en effet. Sans
doute est-ce ce que ce tu as voulu dire ?
Il est défini dans certaines configurations proposées
par l'IDE.
Ben voilà, on y arrive :)(Et est-ce que tu as déjà trouvé un
défaut quelconque qui convient sans modification à ton
environement et à ta mode de travailler ?)
Non, en effet.
J'utilise VC++ depuis quelque semaines, et je n'y ai pas
trouvé un mode debug non plus.
Et comme tu l'utilises en ligne de commande, ainsi que tu l'as
dit dans un autre post, c'est normal :)
Mais tout le monde n'est pas masochiste comme toi ;) Quelle
idée de ne pas utiliser l'IDE :) Moi j'aime bien utiliser
l'IDE je trouve ça très pratique. Emacs et les makefiles j'ai
passé l'âge.
Ce "mode debug" ou "configuration debug" si tu préfères est
évidemment une cuisine de l'IDE.
Et c'est où, cette « mode release »
Oh... juste à côté du "mode debug" ;)
J'utilise aussi VC++ 2005, et je ne l'ai pas trouvé.
Tu n'utilises pas VC++ Tu utilises cl 2005, i.e le compilateur
de VC++ 2005 Dans VC++ il y a V qui signifie Visual, ce que
tout le monde comprend comme l'IDE complet :-)
Le comportement par défaut de VC++, c'est de ne pas définir
NDEBUG.
Le comportement par défaut de VC++ (avec un V comme Visual,
donc, l'IDE) est bien de définir par défaut NDEBUG en "mode
relase" :)
Le compilateur, cl, lui ne définit rien du tout en effet. Sans
doute est-ce ce que ce tu as voulu dire ?
Il est défini dans certaines configurations proposées
par l'IDE.
Ben voilà, on y arrive :)
(Et est-ce que tu as déjà trouvé un
défaut quelconque qui convient sans modification à ton
environement et à ta mode de travailler ?)
Non, en effet.
J'utilise VC++ depuis quelque semaines, et je n'y ai pas
trouvé un mode debug non plus.
Et comme tu l'utilises en ligne de commande, ainsi que tu l'as
dit dans un autre post, c'est normal :)
Mais tout le monde n'est pas masochiste comme toi ;) Quelle
idée de ne pas utiliser l'IDE :) Moi j'aime bien utiliser
l'IDE je trouve ça très pratique. Emacs et les makefiles j'ai
passé l'âge.
Ce "mode debug" ou "configuration debug" si tu préfères est
évidemment une cuisine de l'IDE.Et c'est où, cette « mode release »
Oh... juste à côté du "mode debug" ;)
J'utilise aussi VC++ 2005, et je ne l'ai pas trouvé.
Tu n'utilises pas VC++ Tu utilises cl 2005, i.e le compilateur
de VC++ 2005 Dans VC++ il y a V qui signifie Visual, ce que
tout le monde comprend comme l'IDE complet :-)
Le comportement par défaut de VC++, c'est de ne pas définir
NDEBUG.
Le comportement par défaut de VC++ (avec un V comme Visual,
donc, l'IDE) est bien de définir par défaut NDEBUG en "mode
relase" :)
Le compilateur, cl, lui ne définit rien du tout en effet. Sans
doute est-ce ce que ce tu as voulu dire ?
Il est défini dans certaines configurations proposées
par l'IDE.
Ben voilà, on y arrive :)(Et est-ce que tu as déjà trouvé un
défaut quelconque qui convient sans modification à ton
environement et à ta mode de travailler ?)
Non, en effet.
(Je ne suis pas convaincu non plus qu'il
soit mieux que vim ou emacs, mais puisque je ne le connais pas,
je ne peux pas dire.)
quelconque, que ce soit le défaut du compilateur même, ou un
défaut proposé par l'IDE. Si tu cliques un bouton, sans savoir
ce qu'il fait, c'est bien ta faute, et non celui du compilateur.
(Je ne suis pas convaincu non plus qu'il
soit mieux que vim ou emacs, mais puisque je ne le connais pas,
je ne peux pas dire.)
quelconque, que ce soit le défaut du compilateur même, ou un
défaut proposé par l'IDE. Si tu cliques un bouton, sans savoir
ce qu'il fait, c'est bien ta faute, et non celui du compilateur.
(Je ne suis pas convaincu non plus qu'il
soit mieux que vim ou emacs, mais puisque je ne le connais pas,
je ne peux pas dire.)
quelconque, que ce soit le défaut du compilateur même, ou un
défaut proposé par l'IDE. Si tu cliques un bouton, sans savoir
ce qu'il fait, c'est bien ta faute, et non celui du compilateur.
Pierre Barbier de Reuille wrote:Sylvain Togni wrote:Dans ce cas je teste :
1 - exécution sans gestion d'erreur (Time without errors)
2 - exécution avec exception (chaque appel lance une exception ou
presque)
3 - exécution avec gestion des exception mais sans levée d'exception
4 - avec exception, mais peu d'exceptions sont effectivement levées
5 - erreur par valeurs de retour (pratiquement tous les appels génères
des erreurs)
6 - erreur par valeurs de retour (peu d'erreurs relevées)
Voici les temps que j'obtiens chez moi (compilé avec g++
avec les options par défaut):
Time without errors : 1.28000 sec
Time with exceptions : 89.0000 sec
Time with (no) exceptions : 1.31000 sec
Time with (few) exceptions : 2.03000 sec
Time with return values : 2.33000 sec
Time with (few) return values : 2.34000 sec
La bonne performance du 3 viens du test effectué (i < 0) par
rapport aux autres tests (i%10 == 0 ou i%100000 == 0).
Parmi d'autres choses. Les résultats dépendent beaucoup de
l'implémentation. C'est donc extrèmement difficile à tirer des
conclusions concrètes.
En effet, mais chez moi ça donne des résultats pour le moins bizarre ...
Time without errors : 2.04000 sec
Time with exceptions : 90.0000 sec
Time with (no) exceptions : 2.12000 sec <--
Time with (few) exceptions : 2.06000 sec <--
Time with return values : 2.34000 sec
Time with (few) return values : 2.35000 sec
Comment le fait de ne pas lever d'exception peut être plus
lent ? Bizarre ... bizarre ...
Est-ce réproducible ? Fais tourner tes tests une dizaine de
fois, pour avoir une idée des variations aléatoires dans tes
mesures. (Méfie-toi de la granularité. Même si _SC_CLK_TCK est
élevé, ce n'est pas dit que tu en as une granularité
correspondante.)
Méfie-toi aussi des effets de pagination. Faire tourner chaque
test une fois sans compter le temps, pour être certain qu'il est
dans la mémoire principale, et non encore sur disque.
[...]
Je repète : dans la pratique, je n'ai jamais rencontré un cas
où la différence était assez pour qu'elle joue un rôle dans le
choix. Les motivations du choix tiennent toujours de la
lisibilité et de la maintainabilité. Uniquement.
En gros, plus une erreur est fréquentes, et plus il y a de
chances qu'il faut la traiter localement, plus les code de
retour sont indiqués. Plus l'erreur est rare, et plus il y de
chances qu'il faut la propager loins, plus l'exception s'impose.
Ou exactement on tire la ligne est plutôt une question
d'appréciation personnelle, je crois, même s'il doit y avoir un
consensus aux deux extrèmes.
En ce qui concerne la validation du code, il est possible de
vérifier dans les tests que le code de retour est testé, même
sans provoquer l'erreur ; pour vérifier qu'on n'a pas oublié un
try/catch, il faut provoquer l'erreur. Mais à mon avis, un jeu
de tests qui ne provoque pas l'erreur n'est pas complet ; c'est
donc une différence negligeable.Après, si c'est plus un retour à traiter différemment (i.e.
qqch qui arrive fréquemment), alors une valeur de retour
s'impose.
Mais c'est une autre situation.
Un argument supplémentaire pour les exceptions, évidemment,
c'est la possibilité d'encapsuler plus d'information en ce qui
concerne l'erreur, au moins d'une façon simple.
--
James Kanze GABI Software
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
Pierre Barbier de Reuille wrote:
Sylvain Togni wrote:
Dans ce cas je teste :
1 - exécution sans gestion d'erreur (Time without errors)
2 - exécution avec exception (chaque appel lance une exception ou
presque)
3 - exécution avec gestion des exception mais sans levée d'exception
4 - avec exception, mais peu d'exceptions sont effectivement levées
5 - erreur par valeurs de retour (pratiquement tous les appels génères
des erreurs)
6 - erreur par valeurs de retour (peu d'erreurs relevées)
Voici les temps que j'obtiens chez moi (compilé avec g++
avec les options par défaut):
Time without errors : 1.28000 sec
Time with exceptions : 89.0000 sec
Time with (no) exceptions : 1.31000 sec
Time with (few) exceptions : 2.03000 sec
Time with return values : 2.33000 sec
Time with (few) return values : 2.34000 sec
La bonne performance du 3 viens du test effectué (i < 0) par
rapport aux autres tests (i%10 == 0 ou i%100000 == 0).
Parmi d'autres choses. Les résultats dépendent beaucoup de
l'implémentation. C'est donc extrèmement difficile à tirer des
conclusions concrètes.
En effet, mais chez moi ça donne des résultats pour le moins bizarre ...
Time without errors : 2.04000 sec
Time with exceptions : 90.0000 sec
Time with (no) exceptions : 2.12000 sec <--
Time with (few) exceptions : 2.06000 sec <--
Time with return values : 2.34000 sec
Time with (few) return values : 2.35000 sec
Comment le fait de ne pas lever d'exception peut être plus
lent ? Bizarre ... bizarre ...
Est-ce réproducible ? Fais tourner tes tests une dizaine de
fois, pour avoir une idée des variations aléatoires dans tes
mesures. (Méfie-toi de la granularité. Même si _SC_CLK_TCK est
élevé, ce n'est pas dit que tu en as une granularité
correspondante.)
Méfie-toi aussi des effets de pagination. Faire tourner chaque
test une fois sans compter le temps, pour être certain qu'il est
dans la mémoire principale, et non encore sur disque.
[...]
Je repète : dans la pratique, je n'ai jamais rencontré un cas
où la différence était assez pour qu'elle joue un rôle dans le
choix. Les motivations du choix tiennent toujours de la
lisibilité et de la maintainabilité. Uniquement.
En gros, plus une erreur est fréquentes, et plus il y a de
chances qu'il faut la traiter localement, plus les code de
retour sont indiqués. Plus l'erreur est rare, et plus il y de
chances qu'il faut la propager loins, plus l'exception s'impose.
Ou exactement on tire la ligne est plutôt une question
d'appréciation personnelle, je crois, même s'il doit y avoir un
consensus aux deux extrèmes.
En ce qui concerne la validation du code, il est possible de
vérifier dans les tests que le code de retour est testé, même
sans provoquer l'erreur ; pour vérifier qu'on n'a pas oublié un
try/catch, il faut provoquer l'erreur. Mais à mon avis, un jeu
de tests qui ne provoque pas l'erreur n'est pas complet ; c'est
donc une différence negligeable.
Après, si c'est plus un retour à traiter différemment (i.e.
qqch qui arrive fréquemment), alors une valeur de retour
s'impose.
Mais c'est une autre situation.
Un argument supplémentaire pour les exceptions, évidemment,
c'est la possibilité d'encapsuler plus d'information en ce qui
concerne l'erreur, au moins d'une façon simple.
--
James Kanze GABI Software
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
Pierre Barbier de Reuille wrote:Sylvain Togni wrote:Dans ce cas je teste :
1 - exécution sans gestion d'erreur (Time without errors)
2 - exécution avec exception (chaque appel lance une exception ou
presque)
3 - exécution avec gestion des exception mais sans levée d'exception
4 - avec exception, mais peu d'exceptions sont effectivement levées
5 - erreur par valeurs de retour (pratiquement tous les appels génères
des erreurs)
6 - erreur par valeurs de retour (peu d'erreurs relevées)
Voici les temps que j'obtiens chez moi (compilé avec g++
avec les options par défaut):
Time without errors : 1.28000 sec
Time with exceptions : 89.0000 sec
Time with (no) exceptions : 1.31000 sec
Time with (few) exceptions : 2.03000 sec
Time with return values : 2.33000 sec
Time with (few) return values : 2.34000 sec
La bonne performance du 3 viens du test effectué (i < 0) par
rapport aux autres tests (i%10 == 0 ou i%100000 == 0).
Parmi d'autres choses. Les résultats dépendent beaucoup de
l'implémentation. C'est donc extrèmement difficile à tirer des
conclusions concrètes.
En effet, mais chez moi ça donne des résultats pour le moins bizarre ...
Time without errors : 2.04000 sec
Time with exceptions : 90.0000 sec
Time with (no) exceptions : 2.12000 sec <--
Time with (few) exceptions : 2.06000 sec <--
Time with return values : 2.34000 sec
Time with (few) return values : 2.35000 sec
Comment le fait de ne pas lever d'exception peut être plus
lent ? Bizarre ... bizarre ...
Est-ce réproducible ? Fais tourner tes tests une dizaine de
fois, pour avoir une idée des variations aléatoires dans tes
mesures. (Méfie-toi de la granularité. Même si _SC_CLK_TCK est
élevé, ce n'est pas dit que tu en as une granularité
correspondante.)
Méfie-toi aussi des effets de pagination. Faire tourner chaque
test une fois sans compter le temps, pour être certain qu'il est
dans la mémoire principale, et non encore sur disque.
[...]
Je repète : dans la pratique, je n'ai jamais rencontré un cas
où la différence était assez pour qu'elle joue un rôle dans le
choix. Les motivations du choix tiennent toujours de la
lisibilité et de la maintainabilité. Uniquement.
En gros, plus une erreur est fréquentes, et plus il y a de
chances qu'il faut la traiter localement, plus les code de
retour sont indiqués. Plus l'erreur est rare, et plus il y de
chances qu'il faut la propager loins, plus l'exception s'impose.
Ou exactement on tire la ligne est plutôt une question
d'appréciation personnelle, je crois, même s'il doit y avoir un
consensus aux deux extrèmes.
En ce qui concerne la validation du code, il est possible de
vérifier dans les tests que le code de retour est testé, même
sans provoquer l'erreur ; pour vérifier qu'on n'a pas oublié un
try/catch, il faut provoquer l'erreur. Mais à mon avis, un jeu
de tests qui ne provoque pas l'erreur n'est pas complet ; c'est
donc une différence negligeable.Après, si c'est plus un retour à traiter différemment (i.e.
qqch qui arrive fréquemment), alors une valeur de retour
s'impose.
Mais c'est une autre situation.
Un argument supplémentaire pour les exceptions, évidemment,
c'est la possibilité d'encapsuler plus d'information en ce qui
concerne l'erreur, au moins d'une façon simple.
--
James Kanze GABI Software
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
"kanze" writes:
[...]
| La seule chose à ajouter, c'est que si tu écris une
| bibliothèque, et tu ne sais pas trop où le client va traiter
| l'erreur, il vaut mieux pécher du côté du code de retour.
| Simplement parce que c'est beaucoup plus facile au client
| d'écrire :
| if ( f() != OK ) throw whatever ;
| que d'écrire :
|
| try {
| f() ;
| } catch ( Whatever& error ) {
| // ...
| }
Je driais exactement l'opposé.
"kanze" <kanze@gabi-soft.fr> writes:
[...]
| La seule chose à ajouter, c'est que si tu écris une
| bibliothèque, et tu ne sais pas trop où le client va traiter
| l'erreur, il vaut mieux pécher du côté du code de retour.
| Simplement parce que c'est beaucoup plus facile au client
| d'écrire :
| if ( f() != OK ) throw whatever ;
| que d'écrire :
|
| try {
| f() ;
| } catch ( Whatever& error ) {
| // ...
| }
Je driais exactement l'opposé.
"kanze" writes:
[...]
| La seule chose à ajouter, c'est que si tu écris une
| bibliothèque, et tu ne sais pas trop où le client va traiter
| l'erreur, il vaut mieux pécher du côté du code de retour.
| Simplement parce que c'est beaucoup plus facile au client
| d'écrire :
| if ( f() != OK ) throw whatever ;
| que d'écrire :
|
| try {
| f() ;
| } catch ( Whatever& error ) {
| // ...
| }
Je driais exactement l'opposé.