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

  FORUM HardWare.fr
  Programmation
  C

  Pourquoi dans ce tri a bulle.... ?

 


 Mot :   Pseudo :  
 
Bas de page
Auteur Sujet :

Pourquoi dans ce tri a bulle.... ?

n°1979318
lassault1
Posté le 31-03-2010 à 10:16:36  profilanswer
 

Bonjour a tous :)
 
Pourquoi dans ce code il tri correctement sauf le 1er chiffre?
 

Code :
  1. void ordonnerTableau(long tableau[], long tailleTableau);
  2. int main(int argc, char *argv[])
  3. {
  4.     long tableau[10] = {2, 4, 3, 1, 15, 6, 9, 16, 19, 12};
  5.     long i = 0;
  6.     ordonnerTableau(tableau, 10);
  7.     for(i = 0; i < 10; i++)
  8.     {
  9.         printf("%ld\n", tableau[i]);
  10.     }
  11.     return 0;
  12. }
  13. void ordonnerTableau(long tableau[], long tailleTableau)
  14. {
  15.     long i, a = 0;
  16.      for(i = 0; i < tailleTableau-1; i++)
  17.         {
  18.             if(tableau[i] > tableau[i+1])
  19.             {
  20.                 a = tableau[i+1];
  21.                 tableau[i+1] = tableau[i];
  22.                 tableau[i] = a;
  23.                 i = 0;
  24.             }
  25.         }
  26. }


 
résultat :
 
2
1
3
4
6
9
12
15
16
19

mood
Publicité
Posté le 31-03-2010 à 10:16:36  profilanswer
 

n°1979329
Elmoricq
Modérateur
Posté le 31-03-2010 à 10:34:24  profilanswer
 

Quand tu permutes un élément, tu remets ensuite i à 0. Sauf que tu es dans une boucle for, et i est incrémenté automatiquement au début de chaque itération. Donc i n'est égal à 0 qu'une seule fois dans sa vie, et c'est lors de la toute première itération.

 

En règle générale, c'est une mauvaise pratique que de modifier l'itérateur d'une boucle for. Lorsque l'itérateur est amené à être modifié, il est plus propre de passer par while(), par exemple :

 
Code :
  1. long i = 0;
  2. while ( i < (tailleTableau - 1) ) {
  3.    if ( tableau[i] > tableau[i+1] ) {
  4.        // Permutation
  5.        i = 0;
  6.    }
  7.    else
  8.        ++i;
  9. }


Message édité par Elmoricq le 31-03-2010 à 10:35:37
n°1979347
gilou
Modérateur
Modzilla
Posté le 31-03-2010 à 11:10:04  profilanswer
 

lassault1 a écrit :

Bonjour a tous :)

 

Pourquoi dans ce code il tri correctement sauf le 1er chiffre?

 
Code :
  1. void ordonnerTableau(long tableau[], long tailleTableau);
  2. int main(int argc, char *argv[])
  3. {
  4.     long tableau[10] = {2, 4, 3, 1, 15, 6, 9, 16, 19, 12};
  5.     long i = 0;
  6.     ordonnerTableau(tableau, 10);
  7.     for(i = 0; i < 10; i++)
  8.     {
  9.         printf("%ld\n", tableau[i]);
  10.     }
  11.     return 0;
  12. }
  13. void ordonnerTableau(long tableau[], long tailleTableau)
  14. {
  15.     long i, a = 0;
  16.      for(i = 0; i < tailleTableau-1; i++)
  17.         {
  18.             if(tableau[i] > tableau[i+1])
  19.             {
  20.                 a = tableau[i+1];
  21.                 tableau[i+1] = tableau[i];
  22.                 tableau[i] = a;
  23.                 i = 0;  // La i est remis a zero
  24.             }
  25.         } // et la i passe a 1 avant de revenir en début de boucle a cause de ton i++ en fin de boucle for
  26. }
 

résultat :

 

2
1
3
4
6
9
12
15
16
19

Comme i passe a 1 en début de nouvelle boucle, tableau[0] n'est comparé avec tableau[1] que la toute première fois que ordonnerTableau est exécutée.
Si tu remplaces ton i = 0; par i = -1; tout rentrera dans l'ordre.

 
Citation :

En règle générale, c'est une mauvaise pratique que de modifier l'itérateur d'une boucle for.

Quand on apprend a programmer oui. Quand on est un programmeur C expérimenté qui documente son code pour signaler ce type d'effet de bord sournois, non. (Bon, on serait pas en C, mais dans un vrai langage évolué avec une vrai notion d'itérateur, j'aurais une autre opinion, certes)

 

A+,

Message cité 1 fois
Message édité par gilou le 31-03-2010 à 11:14:34

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°1979349
Elmoricq
Modérateur
Posté le 31-03-2010 à 11:22:59  profilanswer
 

gilou a écrit :


Citation :

En règle générale, c'est une mauvaise pratique que de modifier l'itérateur d'une boucle for.

Quand on apprend a programmer oui. Quand on est un programmeur C expérimenté qui documente son code pour signaler ce type d'effet de bord sournois, non.


 
J'ai tendance à croire que si l'on est obligé de commenter une pratique de code aussi triviale que celle-ci, c'est qu'il y a quelque chose de crade au royaume du Danemark. :o
Mais là chacun voit midi à sa porte, de toute façon j'ai bien noté "en règle générale", parce que les itérateurs ne sont pas toujours des int, et qu'il y a toujours des cas tordus qui trainent. [:dawao]

n°1979378
gilou
Modérateur
Modzilla
Posté le 31-03-2010 à 11:48:51  profilanswer
 

Citation :

si l'on est obligé de commenter une pratique de code aussi triviale que celle-ci

Tu sais jamais qui fera la maintenance de ton code.
Plusieurs dizaines de millier de lignes de mon code écrites il y a une dizaine d'années sont maintenant maintenues par des programmeurs indiens sous-payé de Bangalore, alors...
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°1979388
Elmoricq
Modérateur
Posté le 31-03-2010 à 11:55:45  profilanswer
 

Je n'ai pas de doute sur le fait que ceci DOIT être commenté lorsque cela se produit, et c'est justement ce qui m'ennuie (relis ma phrase ;) ).

n°1979394
lassault1
Posté le 31-03-2010 à 11:58:35  profilanswer
 

Merci a vous..

n°1979427
lassault1
Posté le 31-03-2010 à 12:43:46  profilanswer
 

Elmoricq c'est pas plutôt  i++ que ++i ?

n°1979430
gilou
Modérateur
Modzilla
Posté le 31-03-2010 à 12:48:58  profilanswer
 

Elmoricq a écrit :

Je n'ai pas de doute sur le fait que ceci DOIT être commenté lorsque cela se produit, et c'est justement ce qui m'ennuie (relis ma phrase ;) ).

C'est une question d'opinion.
Je pense pour ma part que le message passé a un futur mainteneur est plus clair avec un  
for (int i=0; 0<max; i++) en une seule ligne  
qu'avec un  
int i = 0;
while (i<max)
...
++i;
sur plusieurs lignes pas successives pour certaines.
 
A+,


---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
n°1979433
gilou
Modérateur
Modzilla
Posté le 31-03-2010 à 12:51:41  profilanswer
 

lassault1 a écrit :

Elmoricq c'est pas plutôt  i++ que ++i ?


C'est pareil, vu que c'est une instruction indépendante ici. Sur certaines implémentations, autrefois, ++i était plus rapide dans certains cas (de nos jours, un compilo doit générer le même code sur ce type de ligne, sinon, son développeur mérite le knout).
 
Bon, je suis plus en ligne pour 24h.
A+,


Message édité par gilou le 31-03-2010 à 12:53:43

---------------
There's more than what can be linked! --    Iyashikei Anime Forever!    --  AngularJS c'est un framework d'engulé!  --
mood
Publicité
Posté le 31-03-2010 à 12:51:41  profilanswer
 

n°1979478
Elmoricq
Modérateur
Posté le 31-03-2010 à 13:37:25  profilanswer
 

gilou a écrit :

C'est une question d'opinion.


 
Clairement, on entre ici dans le domaine du "autant de pratiques que de développeurs". [:romf]

n°1979505
Un Program​meur
Posté le 31-03-2010 à 13:49:03  profilanswer
 

lassault1 a écrit :

Elmoricq c'est pas plutôt  i++ que ++i ?


 
En C, quand les deux sont possibles il n'y a pas de raisons de preferer l'un a l'autre sans tomber dans de la micro-optimisation compulsive (et aleatoire, les compilateurs optimiseurs etant capables de generer le meme code).  Historiquement, i++ est plus frequent.
 
En C++, ++i retournant une référence vers i et i++ retournant un temporaire contenant l'ancienne valeur de i, il faut penser au coût de construction et de destruction de ce temporaire.  Pour les types de base, le compilateur se retrouve dans la même situation que pour le C.  Pour des iterateurs -- en particulier pour des iterateurs un peu complexe, d'une map ou d'une deque par exemple -- il pourrait avoir une différence mesurable.  Et dans du code générique, on ne sait pas a priori si on se trouve dans le cas ou c'est mesurable ou non.  L'utilisation de ++i s'est donc répandue.  Mais ceux qui ont essaye avec les conteneurs standards on eu beaucoup de mal a mesurer une différence qui ne soit pas négligeable, sans parler de le faire dans un contexte ou on fait réellement quelque chose pendant l'itération.


---------------
The truth is rarely pure and never simple (Oscar Wilde)
n°1979514
Elmoricq
Modérateur
Posté le 31-03-2010 à 13:56:25  profilanswer
 

Je ne savais même pas qu'il y avait (eu) une différence entre les deux syntaxes en termes de performances (je ne parle pas en terme d'interprétation dans une expression, évidemment).
 
Ici, j'ai écrit "++i" par habitude.


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

  Pourquoi dans ce tri a bulle.... ?

 

Sujets relatifs
[VBSCRIPT] Modifier nom affiché sur le bureau pour "Mes documents"différences tri à bulle et par permutation
création d'une info bulleTri à bulle (forme recursif)!!!!!!!
Passer une variable a une info bulle?Info bulle sur un bouton sur une feuille.
Info Bulles perso dans <area coord...>pb de positionnement bulle au survol en javascript
JS : div "info bulle" qui depasse du conteneurprobleme de position pour un info bulle
Plus de sujets relatifs à : Pourquoi dans ce tri a bulle.... ?


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