OVH Cloud OVH Cloud

Bug indétectable via printf() / cout

148 réponses
Avatar
AG
Bonjour =E0 tous,

Je travaille dans une =E9quipe de personnes pour lesquels le d=E9bugger
n'est pas l'outil qui tombe sous le sens lorsqu'il s'agit de trouver
les bugs des outils qu'ils ont d=E9velopp=E9.

Afin de les sensibiliser, je recherche un exemple de bug difficile
(voir impossible) a d=E9tecter via des printf()/cout qui n'afficheraient
que les contenus des variables. (Je me rends bien compte qu'on doit
pouvoir tout d=E9bugger avec printf()/cout, mais il faut parfois
afficher les adresses des variable (en plus de leur valeur), voir
parfois la m=E9moire =E0 certains endroits.)

Je voudrais construire un exemple simple (notions de C++ pas trop
compliqu=E9es) et court (un seul fichier, 100 lignes max) pour qu'on
puisse l'=E9tudier en un quart d'heure, mais le d=E9bugger en un temps
presque infini sans d=E9bugger.

Il est possible que l'exemple, puisqu'il y a un bug, d=E9pende de la
plateforme mais c'est un peu in=E9vitable.

L'id=E9al serait que le plantage ait lieu bien apr=E8s le bug...=E7a rajout=
e
du piment. Bref, vous voyez l'id=E9e quoi...

J'avais plusieurs pistes d'exploitation de bug:

Piste 1:
Boucle for d=E9croissante sur un entier non sign=E9 : for(size_t i =3D N;
0<=3D i; i--)

Piste 2:
comparaison de double : double x; ... ; x =3D=3D 0.0

Piste 3:
retour de malloc() non test=E9

Piste 4:
caract=E8re de fin de ligne non test=E9 (\0)

Mais jusque l=E0, je crains qu'il ne soit trop facile de d=E9tecter le
bug

J'ai donc ensuite pens=E9 aux r=E9f=E9rences. Mais ce code est encore un pe=
u
trop voyant. Dans le main(), on peut facilement se demander pourquoi
f1 et f2 sont des r=E9f=E9rences, ce qui met directement la puce =E0
l'oreille. Peut =EAtre trouvez vous ce code bien trop compliqu=E9, ou
auriez vous en t=EAte un mani=E8re de "l'am=E9liorer" :-)

A bon entendeur salut.

AG.




#include <iostream>

using namespace std;

#define BUFFER_LENGTH 10

template<int N, class T>
class fifo_circular
{
private:
T * position;
size_t pos_offset;
T buffer[N];

public:
fifo_circular() { pos_offset =3D N-1; position =3D buffer + pos_offset;
for(int i=3D0;i<N;i++) buffer[i]=3DT(0);};

T step(T &input)
{
*position =3D input;

if(pos_offset>0) // ici il y aurait peut =EAtre moyen de glisser le
bug de la piste 1
pos_offset--;
else
pos_offset =3D N-1;

position =3D buffer + pos_offset;
return *position;
};

template<int M, class U> friend ostream & operator<<(ostream & o,
const fifo_circular<M,U> &f);
};

template<int N, class T>
fifo_circular<N,T> & Init(T & value)
{
fifo_circular<N,T> & f =3D fifo_circular<N,T>(); // h=E9 h=E9 h=E9

for(size_t i =3D 0; i < N; i++)
f.step(value);
return f;
}

template<int M, class U>
ostream & operator<<(ostream & o, const fifo_circular<M,U> &f)
{
for(size_t i =3D 0; i < M; i++)
o << f.buffer[i] << " ";
return o;
}

int main(int argc, char * argv[])
{
int a =3D 1;
fifo_circular<5,int> & f1 =3D Init<5,int>(a); // ici, c'est un peu trop
voyant. On se demande pourquoi f1 est d=E9clar=E9 en tant que
r=E9f=E9rence...
a =3D 2;
fifo_circular<5,int> & f2 =3D Init<5,int>(a);

cout << "fifo f1: " << f1 << "\n";
cout << "fifo f2: " << f2 << "\n";

return 0;
}

10 réponses

Avatar
ld
On 30 nov, 15:15, Marc Boyer wrote:
Le 30-11-2009, AG a écrit :
> On Nov 30, 2:27 pm, Marc Boyer
> wrote:
>>   Mais est-ce grave ? J'avoue ne quasiment jamais me servir
>> de débugger. Je travaille surtout en précondition/invariant
>> (assert) + tests unitaires, et éventuellementvalgrind
>> quand je soupsonne une corruption mémoire.

>>   Et une fois le bug identifié, à grand coups de cerr
>> + assert.

>>   D'autant que souvent, le bug n'apparait pas en mode débug ;-)



C'est pourquoi je compile toujours avec le meme niveau d'optimisaton.

  En plus, les precond/invariants servent aussi de documentation,
et puis tu les écris quand tu écris la fonctions, donc tu sais ce
que ça va faire.



tout a faire d'accord.

  Et puis c'est aussi facile d'écrire
PRINT_VALUE(toto)
  avec une macro du type
#define PRINT_VALUE(X)         if (debug) { cerr<<#X "="<<(X)<< endl;}
  que de faire click-gauche, 'suivre-variable'



manque quelques std:: pour des macros globale...

  Et puis les débogueurs que je connaissais ne montraient pas d'histo rique.
Souvent, la question c'est "pourquoi cette var vaut ça ?", et tu remont es
le temps. En affichant les variables en console, la console se souvient.

  De plus, en ce qui concerne les fuites mémoires,valgrindest
bien plus efficace que de suivre pas à pas le débogueur.



C'est surement vrai pour les cas "d'ecole". Perso, j'ai rapidement
atteint les limites de valgrind, des que ton programme manipule qques
100MB de data allouee dynamiquement, il devient beaucoup trop lent (x
1000) et trop gourmand (pas de resultat du tout sur une machine avec 4
GB). Je m'en sers surtout pour debugger les tests unitaires, mais en
conditions reelles, j'utilise d'autres techniques plus efficace...

> Cela dit, qu'on me le dise si les debugger ne sont pas intensivement
> utilisés dans l'industrie, je serais content de me tromper. Dans mon
> entourage, tout ceux à qui j'ai montré un debugger pratique l'ont
> adopté.



quel debuggeur est pratique?

  Non, tests unitaires / assert / printf, c'était la méthodologie.



Elle a l'avantage de marcher avec tous les langages. En ce qui
concerne C/C++, printf (ou n'importe quelle fonction variadic) est
particulierement sensible au "stack corruption". Quand elle plante et
que les formats sont conformes, il y a fort a parier qu'une variable
automatique est corrompue qqpart avant l'appel.

Marc Boyer
--
En prenant aux 10% des francais les plus riches 12% de leurs revenus,
on pourrait doubler les revenus des 10% les plus pauvres.http://www.inega lites.fr/spip.php?article1&id_mot0



Il serait surtout tant de decrire la richesse d'un pays par deciles et
plus "en moyenne". La moyenne masque les inegalites croissantes avec
les 10% "les plus riches" qui arrivent a faire augmenter la moyenne
nationale malgre un appauvrissement des 50% "les plus pauvres"...
M'enfin, c'est comme comptabilise les votes blancs aux elections, les
politiques ne sont pas pres d'accepter de montrer ses chiffres.

a+, ld.

a+, ld.
Avatar
ld
On 30 nov, 17:54, James Kanze wrote:
On Nov 30, 2:15 pm, Marc Boyer
wrote:

> Le 30-11-2009, AG a écrit :

    [...]

> Possible. J'utilisais le deboggeur avant, sous Win* il y a
> plus de 10 ans, puis SunStudio puis ddd/gdb/xemacs, puis plus
> rien...

Je travaille actuellement avec Visual Studios 8 ; il offre bien
moins de possibilités que gdb (ou au moins, je ne les ai pas
trouvé).

    [...]

> Non, tests unitaires / assert / printf, c'était la méthodologie.

À règle générale, dans des boîtes bien organisées, il est
interdit d'utiliser le deboggeur tant qu'on n'a pas de test
unitaire qui montre le problème. On ne veut pas qu'il
reapparaissent dans une version future, et on veut être sûr que
les tests unitaires le détectent. Et la plupart du temps, une
fois qu'on a isolé le problème assez pour définir un test
unitaire qui le declenche, on l'a isolé assez pour pouvoir
savoir exactement ce qui ne va pas d'après les symptomes.

> On présentait gdb/ddd en illustration des cours sur
> l'allocation dynamique, pour qu'ils "voient" leurs listes
> chainées.
> Et quand en projet ils galéraient à rechercher un bug, et
> qu'ils finissaient par m'appeller, au bord de la crise,
> parfois me montraient leur problème avec gdb/ddd, mais
> toujours, j'allais à la pèche aux infos à coup
> d'assert/printf, et, éventuellementvalgrind.

Je ne suis pas sûr d'être d'accord avec l'utilisation du printf,
mais en général, il faut dire que si tu as besoin d'une
information une fois, tu en aurais besoin une autre fois, et
qu'il faut alors y introduire un log ou un trace.



seulement s'il s'agit de pre-conditions (au sens DBC), c'est a dire ce
qui est suceptible de varier pendant l'utilisation du logiciel. Les
post-conditions valident "les etats intermes" des algorithmes et les
invariants "les etats externes" des algorithmes. Ce sont des
proprietes des specs, pas du runtime qui est dependant de l'input.
Donc une fois que l'application est qualifiee, ils devraient pouvoir
etre deactives tandis que les pre-conditions devraient rester
actives.

(Mais ça ne
vaut que pour les programmes « industriels » ; je vois mal un
élève, même à l'univerité, se servir extensivement des logs.)



Au contraire, cela me parait etre un point essentiel de la pedagogie.
De plus en environnement concurrenciel, parallele ou distribue, il n'y
a pas d'autre methode qui marche sur de vrais programmes.

a+, ld.
Avatar
Michael Doubez
On 9 déc, 10:49, "Senhon" wrote:
"James Kanze" a écrit dans le message de groupe de
discussion :


> On Dec 9, 7:49 am, "Senhon" wrote:

> Peut-être le problème que certains (comme moi-même) apercoivent
> avec les IDE, c'est qu'ils permettent ce genre de dévelopement.

Vaste débat : est-ce le produit ou l'usage ?



AMHA la souris: elle mets la personne en mode visuel et il devient
plus facile de cliquer sur ce qu'on voit que sur ce qu'on veut faire.
Puis une fois que la souris en en main, c'est idiot de la lacher pour
tappe un raccourci.

Quand on a l'habitude des raccourcis, c'est plus facile de garder
cette habitude (quite a les redéfinir pout ne pas être dépaysé).

> Tandis que devant la ligne de commande Unix, il faut bien
> apprendre un peu.

Attitude un peu nostalgique, non ?



La souris permet la prise en main rapide d'un produit (je vois les
opérations en clair) et des convetions usuelles permettent de s'y
retrouver (sauf dans excel 2007).
Une interface texte, il faut savoir que ':w' permet de sauver sous vim
(CTRL-X CTRL-W sous emacs) et donc il y a forcément un temps
d'apprentissage pour savoir comment faire les choses.

--
Michael
Avatar
loic.actarus.joly
> Un cas simple, dans un .CPP je tape , par exemple : <Declarateur> <NomObj et>
, (eventuellement suivi d'une initialisation) suivi d'un jeu de touches
pour, être précis 2.
La macro qui est lancée va lire la ligne sur laquelle je suis, extraire le
nom de <Declarateur> (qui peux être une déclaration quelconque : poin teur,
référence, classe, classe paramétrée ), puis avec le fichier en c ours
d'édition va déterminer le nom du header et ajouter cette nouvelle
déclaration de l'objet. Et va modifier le fichier courant en supprimant le
<Declateur>.
De même pour une fonction membre, mais là c'est un peu plus complexe, mais
dans la même optique, je tape une ligne et un raccourci, et c'a mouline à ma
place.




Bonjour,

J'utilise pour ma part l'IDE de visual studio en étant pas mal au
clavier, mais ça fait un bout de temps que je me dis que quelques
macros pourraient faciliter et accélérer encore ma rapidité de codage .
Sauf qu'à chaque fois, la barrière d'apprentissage et le temps de mise
en place sont un peu élevées, et du coup je n'ai fait que 2/3 macros,
pas plus, et très simples (mais pour info, mes macros peuvent appeler
un programme externe, donc si vraiment James veut réutiliser des
scripts écrit pour son shell, je pense que la bonne voie est de créer
une macro qui sauve la sélection courante dans un fichier, appèle le
script, puis remplace la sélection courante par le retour).

Je me dis que tes macros pourraient me servir, soit directemetn, soit
comme base d'inspiration. Pourrais-tu les rendre disponibles, ou
penses-tu qu'elles te sont trop spécifiques ?
Avatar
Marc Boyer
Le 09-12-2009, James Kanze a écrit :
On Dec 9, 7:49 am, "Senhon" wrote:
Moi aussi j'ai autour de moi une quantité de personnes qui
font du développement juste à titre alimentaire ( je ne veux
pas les accabler ). Du coup, il se contente très vite et
n'iront pas forcément se casser la tête ...



Peut-être le problème que certains (comme moi-même) apercoivent
avec les IDE, c'est qu'ils permettent ce genre de dévelopement.
Tandis que devant la ligne de commande Unix, il faut bien
apprendre un peu. (Bien que j'ai connu quelques uns qui s'en
sortaient là aussi avec un strict minimum. Si on ne veut pas
apprendre, on n'apprend pas, quelque soit l'environement. Et
vice versa.)



Après avoir vainement essayé de trouver quelque chose qu'un
envionnement permettrait de faire, et pas l'autre, on arrive
à quelque chose de plus connu: la courbe d'apprentissage,
qui trace la productivité vs l'investissement.

Les outils de la famille Unix ont une longue expérience,
et une approche forte productivité mais fort investissement.
Le chercher/remplacer d'un éditeur vs sed + regexp + |,
ça n'a rien à voir en terme de courbes.

Et même si les Unix-like offre de plus en plus d'outils
à accès facile, les outils fort investissement/forte prod
restent la base du système, et très accessibles.
Et les docs présentent souvent les différentes façons
de faire.
Mais des trucs se perdent (la page de man de gnumeric
n'indique pas comment imprimer une page sans l'ouvrir).

Un autre point fort, c'est la stabilité des outils,
donc la pérennité des apprentissages.

Dans le monde Win*, je ne sais pas trop. Je n'ai pas
regardé serieusement depuis des années. Il y a eut l'époque
des évolutions permanentes: COM, DCOM, VB. J'ai eut
l'impression que VB devenait la "glue" standart. Je ne
sais si c'est encore le cas.

Marc Boyer
--
En prenant aux 10% des francais les plus riches 12% de leurs revenus,
on pourrait doubler les revenus des 10% les plus pauvres.
http://www.inegalites.fr/spip.php?article1&id_mot0
Avatar
Senhon
a écrit dans le message de groupe de
discussion :


Bonjour,

J'utilise pour ma part l'IDE de visual studio en étant pas mal au
clavier, mais ça fait un bout de temps que je me dis que quelques
macros pourraient faciliter et accélérer encore ma rapidité de codage.
Sauf qu'à chaque fois, la barrière d'apprentissage et le temps de mise
en place sont un peu élevées, et du coup je n'ai fait que 2/3 macros,
pas plus, et très simples (mais pour info, mes macros peuvent appeler
un programme externe, donc si vraiment James veut réutiliser des
scripts écrit pour son shell, je pense que la bonne voie est de créer
une macro qui sauve la sélection courante dans un fichier, appèle le
script, puis remplace la sélection courante par le retour).

Je me dis que tes macros pourraient me servir, soit directemetn, soit
comme base d'inspiration. Pourrais-tu les rendre disponibles, ou
penses-tu qu'elles te sont trop spécifiques ?



Tu me flattes.

Dans ma dernière version, le fichier ".vsmacro" fait 607 ko ( je ne sais pas
comment c'est composé, car j'en ai surement pas tapé autant), en comparaison
le fichier d'exemple fourni avec VS2008 ("Samples.vsmacros") fait 700ko.
Je ne compte pas les patrons de fichiers (qui compte peanuts en
comparaison).
Les macros, me sont légèrement personnalisées, mais pourraient être
facilement généralisables.

Mais ce qui m'épate c'est que cela ne te dispensera pas de fournir un effort
d'apprentissage, surtout si tu dois les modifier.
As-tu essayé, comme je le disais auparavant, d'utiliser la fonction
d'enregistrement de macro, c'a débroussaille grandement ...
Avatar
ld
On 10 déc, 12:49, Marc Boyer wrote:
Le 09-12-2009, James Kanze a écrit :

> On Dec 9, 7:49 am, "Senhon" wrote:
>> Moi aussi j'ai autour de moi une quantité de personnes qui
>> font du développement juste à titre alimentaire ( je ne veux
>> pas les accabler ).  Du coup, il se contente très vite et
>> n'iront pas forcément se casser la tête ...

> Peut-être le problème que certains (comme moi-même) apercoivent
> avec les IDE, c'est qu'ils permettent ce genre de dévelopement.
> Tandis que devant la ligne de commande Unix, il faut bien
> apprendre un peu. (Bien que j'ai connu quelques uns qui s'en
> sortaient là aussi avec un strict minimum. Si on ne veut pas
> apprendre, on n'apprend pas, quelque soit l'environement. Et
> vice versa.)



Salut Marc,

 Après avoir vainement essayé de trouver quelque chose qu'un
envionnement permettrait de faire, et pas l'autre, on arrive
à quelque chose de plus connu: la courbe d'apprentissage,
qui trace la productivité vs l'investissement.



Quand tu parles de cette courbe, tu penses aux Unixes, a Linux ou a
Posix? Parce que l'ecriture de script _portable_ utilisant ses outils
est loin d'etre simple. Perso je me suis limite a Posix + gmake.

  Les outils de la famille Unix ont une longue expérience,
et une approche forte productivité mais fort investissement.
  Le chercher/remplacer d'un éditeur vs sed + regexp + |,
ça n'a rien à voir en terme de courbes.



meme les regexp ne sont pas portable...

   Et même si les Unix-like offre de plus en plus d'outils
à accès facile, les outils fort investissement/forte prod
restent la base du système, et très accessibles.



Mais pas toujours portable. Il y a souvent des compromis a faire comme
bash, gmake, gawk etc... ce qui revient peut-etre a dire que GNU est
entrain de propager son "standard". En 17 ans de Linux, je me suis
souvent senti "perdu" dans les options des memes outils sur SunOs ou
HPUX par exemple. Certe la philosophie reste la meme, mais ta courbe
n'est pas si "droite" que ca.

  Et les docs présentent souvent les différentes façons
de faire.
   Mais des trucs se perdent (la page de man de gnumeric
n'indique pas comment imprimer une page sans l'ouvrir).

  Un autre point fort, c'est la stabilité des outils,
donc la pérennité des apprentissages.



Heureusement, parce qu'ecrire une (la!) macro sed qui permet d'enlever
les commentaires d'un source C/C++ demande quelques annees de
pratique. Heureusement elle est sur le web quand on sait la
reconnaitre ;-)

Dans le monde Win*, je ne sais pas trop. Je n'ai pas
regardé serieusement depuis des années. Il y a eut l'époque
des évolutions permanentes: COM, DCOM, VB. J'ai eut
l'impression que VB devenait la "glue" standart. Je ne
sais si c'est encore le cas.

Marc Boyer
--
En prenant aux 10% des francais les plus riches 12% de leurs revenus,
on pourrait doubler les revenus des 10% les plus pauvres.http://www.inega lites.fr/spip.php?article1&id_mot0



CF ma suggestion dans mon autre post sur valgrind dans ce meme
thread ;-)

a+, ld.
Avatar
James Kanze
On Dec 10, 9:03 am, ""
wrote:
> Un cas simple, dans un .CPP je tape , par exemple : <Declarateur> <NomO bjet>
> , (eventuellement suivi d'une initialisation) suivi d'un jeu de touches
> pour, être précis 2.
> La macro qui est lancée va lire la ligne sur laquelle je suis, extrai re le
> nom de <Declarateur> (qui peux être une déclaration quelconque : po inteur,
> référence, classe, classe paramétrée ), puis avec le fichier en cours
> d'édition va déterminer le nom du header et ajouter cette nouvelle
> déclaration de l'objet. Et va modifier le fichier courant en supprima nt le
> <Declateur>.
> De même pour une fonction membre, mais là c'est un peu plus complex e, mais
> dans la même optique, je tape une ligne et un raccourci, et c'a mouli ne à ma
> place.



J'utilise pour ma part l'IDE de visual studio en étant pas mal au
clavier, mais ça fait un bout de temps que je me dis que quelques
macros pourraient faciliter et accélérer encore ma rapidité de coda ge.
Sauf qu'à chaque fois, la barrière d'apprentissage et le temps de mis e
en place sont un peu élevées,



« No pain, no gain », comme dit toujours mon fils:-).

et du coup je n'ai fait que 2/3 macros,
pas plus, et très simples (mais pour info, mes macros peuvent appeler
un programme externe, donc si vraiment James veut réutiliser des
scripts écrit pour son shell, je pense que la bonne voie est de créer
une macro qui sauve la sélection courante dans un fichier, appèle le
script, puis remplace la sélection courante par le retour).



Je me dis que tes macros pourraient me servir, soit directemetn, soit
comme base d'inspiration. Pourrais-tu les rendre disponibles, ou
penses-tu qu'elles te sont trop spécifiques ?



Plus intéressant serait de savoir où il a appris de faire des
macros VS, parce que moi, je suis prêt à investir un peu de
temps et d'effort pour les apprendre (vue que je risque de
travailler sous Windows pour pas mal du temps encore).

--
James Kanze
Avatar
Marc Boyer
Le 10-12-2009, ld a écrit :
On 10 déc, 12:49, Marc Boyer wrote:
Le 09-12-2009, James Kanze a écrit :
 Après avoir vainement essayé de trouver quelque chose qu'un
envionnement permettrait de faire, et pas l'autre, on arrive
à quelque chose de plus connu: la courbe d'apprentissage,
qui trace la productivité vs l'investissement.



Quand tu parles de cette courbe, tu penses aux Unixes, a Linux ou a
Posix? Parce que l'ecriture de script _portable_ utilisant ses outils
est loin d'etre simple. Perso je me suis limite a Posix + gmake.



Tu évoques un autre problème: la portabilité et/ou compatibilité.
Win* s'est clairement assis sur le sujet, donc, on ne peut pas
lui reprocher de ne pas tenir ses promesses.

Quand je parlais d'investissement, c'était une question
humaine, pas logicielle, ce n'était pas le fait qu'un
script écrit en 1997 sur SunOS fonctionne en 2009 sur Linux,
mais plutôt que tu retrouves très vite tes habitudes, et que
tu vas assez vite être à même de corriger le truc.

   Et même si les Unix-like offre de plus en plus d'outils
à accès facile, les outils fort investissement/forte prod
restent la base du système, et très accessibles.



Mais pas toujours portable.



Oui, mais à mon sens, c'est un autre problème.

Il y a souvent des compromis a faire comme
bash, gmake, gawk etc... ce qui revient peut-etre a dire que GNU est
entrain de propager son "standard". En 17 ans de Linux, je me suis
souvent senti "perdu" dans les options des memes outils sur SunOs ou
HPUX par exemple. Certe la philosophie reste la meme, mais ta courbe
n'est pas si "droite" que ca.



Non, mais si on te demande de faire la même chose sur Win98 ou
Windows 7, la variation risque d'être encore plus grande, non ?

Marc Boyer
--
En prenant aux 10% des francais les plus riches 12% de leurs revenus,
on pourrait doubler les revenus des 10% les plus pauvres.
http://www.inegalites.fr/spip.php?article1&id_mot0
Avatar
Marc Boyer
Le 09-12-2009, ld a écrit :
  Et puis les débogueurs que je connaissais ne montraient pas d'historique.
Souvent, la question c'est "pourquoi cette var vaut ça ?", et tu remontes
le temps. En affichant les variables en console, la console se souvient.

  De plus, en ce qui concerne les fuites mémoires,valgrindest
bien plus efficace que de suivre pas à pas le débogueur.



C'est surement vrai pour les cas "d'ecole". Perso, j'ai rapidement
atteint les limites de valgrind, des que ton programme manipule qques
100MB de data allouee dynamiquement, il devient beaucoup trop lent (x
1000) et trop gourmand (pas de resultat du tout sur une machine avec 4
GB). Je m'en sers surtout pour debugger les tests unitaires, mais en
conditions reelles, j'utilise d'autres techniques plus efficace...



Quelles techniques ?

En prenant aux 10% des francais les plus riches 12% de leurs revenus,
on pourrait doubler les revenus des 10% les plus pauvres.
http://www.inegalites.fr/spip.php?article1&id_mot0



Il serait surtout tant de decrire la richesse d'un pays par deciles et
plus "en moyenne". La moyenne masque les inegalites croissantes avec
les 10% "les plus riches" qui arrivent a faire augmenter la moyenne
nationale malgre un appauvrissement des 50% "les plus pauvres"...



On s'en fout des inégalités, c'est le PIB qui compte :-(

Marc Boyer
--
En prenant aux 10% des francais les plus riches 12% de leurs revenus,
on pourrait doubler les revenus des 10% les plus pauvres.
http://www.inegalites.fr/spip.php?article1&id_mot0