IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

 C Discussion :

Tri fusion avec pthread


Sujet :

C

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre éclairé
    Inscrit en
    Avril 2007
    Messages
    483
    Détails du profil
    Informations personnelles :
    Âge : 37

    Informations forums :
    Inscription : Avril 2007
    Messages : 483
    Par défaut Tri fusion avec pthread
    Bonjour à tous,

    Voila je dois réaliser un programme en C effectuant un tri par fusion en utilisant les pthreads, et tout cela en 1semaine et sans connaître le C

    on m'a donné le gros de l'algorithme à utiliser (que voici) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
     
    #define SIZE_TAB 5
     
    void fusion(int tableau[], int deb1, int fin1, int fin2);
    void tri_fusion_bis(int tableau[], int deb, int fin, int count);
    void tri_fusion(int tableau[], int longueur);
     
    void affiche_tab(int *tab)
    {
    	int i;
    	for (i = 0; i <= SIZE_TAB; i++)
    	{
    		printf (" %d ", tab[i]);
    	}
    }
     
    void fusion(int tableau[], int deb1, int fin1, int fin2)
    {
    	int *table1;
    	int deb2 = fin1 + 1;
    	int compt1 = deb1;
    	int compt2 = deb2;
    	int i;
     
    	printf (" [deb fusion] --> ");
    	affiche_tab(tableau);
    	printf("\n");
     
    	table1 = malloc((fin1 - deb1 + 1) * sizeof(int));
     
    	//on recopie les éléments du début du tableau
    	for (i = deb1; i <= fin1; i++)
    	{
    		table1[i-deb1] = tableau[i];
    	}
     
    	printf (" cpy tableau \n");
    	for (i = deb1; i <= fin2; i++)
    	{
    		printf (" Elements %d \n", i);
    		if (compt1 == deb2)
    		{
    			printf (" Tous les éléments sont classés. \n");
    			break;
    		}
    		else if (compt2 == fin2 + 1)
    		{
    			tableau[i] = table1[compt1 - deb1];
    			compt1++;
    		}
    		else if (table1[compt1 - deb1] < tableau[compt2])
    		{
    			tableau[i] = table1[compt1 - deb1];
    			compt1++;
    		}
    		else
    		{
    			tableau[i] = tableau[compt2];
    			compt2++;
    		}
    	}
    	free(table1);
     
    	printf (" [fin fusion] --> ");
    	affiche_tab(tableau);
    	printf (" \n");
    }
     
    void tri_fusion_bis(int tableau[], int deb, int fin, int count)
    {
    	sleep(3);
     
    	printf ("[%d] Itération debut %d fin %d \n", count, deb, fin);
     
    	if (deb != fin)
    	{
    		int milieu = (fin + deb) / 2;
     
    		tri_fusion_bis (tableau, deb, milieu, count + 1);
     
    		tri_fusion_bis(tableau, milieu + 1, fin, count + 1);
     
    		fusion(tableau, deb, milieu, fin);
    	}
    }
     
    void tri_fusion(int tableau[], int longueur)
    {
    	if (longueur > 0)
    	{
    		tri_fusion_bis(tableau, 0, longueur - 1, -1); 
    	}
    }
    1ère question : à quoi sert le "#define SIZE_TAB 5" au tout début ??

    J'ai essayé de créer le main pour pouvoir utiliser le programme sans les threads dans un premier temps. J'ai donc fait un truc dans ce genre :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    int main(void)
    {
    	int tableau[8] = {26, 7, 15, 6, 1};
    	int longueur = sizeof(tableau);
     
    	tri_fusion(tableau, longueur);
     
    	return 0;
    }
    Lorsque je lance le programme, au début tout va bien a part un détail : il affiche 6 nombres alors que le tableau n'en contient que 5 (un zero apparait à la fin).

    Ensuite, plus on avance, plus ça "part en live". les nombres du ableau sont au fur é a mesure remplacés par des zeros, seuls le 1 3 et 6 restent, et sont mis après trois zero.

    Enfin une erreur se produit sur la fin
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    5 [main] a 1780 _cygtls::handle_exception: Error while dumping state (probably corrupted stack)
    Segmentation fault (core dumped)
    Je n'ai pas bien saisi l'erreur donc bon...

    Pour info, je teste sous cygwin (un émulateur unix) en compilant le fichier via la commande gcc

    Grand merci d'avance pour votre aide

  2. #2
    Membre averti
    Profil pro
    Inscrit en
    Novembre 2004
    Messages
    53
    Détails du profil
    Informations personnelles :
    Âge : 43
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations forums :
    Inscription : Novembre 2004
    Messages : 53
    Par défaut
    j'ai pas tout regardé mais essaye deja avec comme main :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
     
     
    int main(void)
    {
    	int tableau[5] = {26, 7, 15, 6, 1};
    	int longueur = 5;
     
    	tri_fusion(tableau, longueur);
     
    	return 0;
    }

  3. #3
    Membre éclairé
    Inscrit en
    Avril 2007
    Messages
    483
    Détails du profil
    Informations personnelles :
    Âge : 37

    Informations forums :
    Inscription : Avril 2007
    Messages : 483
    Par défaut
    En effet ca marche mieux

    Mais toujours la meme question : à quoi sert la 1ère ligne "#define SIZE_TAB 5" car pour moi elle a un rapport avec la taille du tableau (je n'ai rien trouvé dessus donc je suis pas sur)

    Et pourquoi ca marche si je donne une valeur directe à longueur et pas si je lui donne comme valeur le sizeof du tableau ?

    J'essaye de comprendre pour pouvoir avancer ...

    Merci d'avance pr les réponses

  4. #4
    Membre éclairé
    Inscrit en
    Avril 2007
    Messages
    483
    Détails du profil
    Informations personnelles :
    Âge : 37

    Informations forums :
    Inscription : Avril 2007
    Messages : 483
    Par défaut
    Autre remarque, il affiche 6 nombres, quelle que soit la taille du tableau

    Si j'ai un tableau à 5 cases j'ai un 47 qui apparait à la fin du tableau, et si j'ai plus de 6 cases il n'affiche que les 6 premières

  5. #5
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 395
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 395
    Par défaut
    C'est parce que la fonction d'affichage est erronée.
    Il faut:
    1. remplacer le <= par <
    2. soit utiliser SIZE_TAB correctement, soit passer la longueur en paramètre (de type size_t)
    3. changer le type de i en size_t.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  6. #6
    Membre éclairé
    Inscrit en
    Avril 2007
    Messages
    483
    Détails du profil
    Informations personnelles :
    Âge : 37

    Informations forums :
    Inscription : Avril 2007
    Messages : 483
    Par défaut
    Citation Envoyé par Médinoc Voir le message
    [*]soit utiliser SIZE_TAB correctement, soit passer la longueur en paramètre (de type size_t)[/LIST]
    Justement, je ne sais pas à quoi sert ce SIZE_TAB ... pourrais-tu m'expliquer ?

  7. #7
    Membre averti
    Profil pro
    Inscrit en
    Novembre 2004
    Messages
    53
    Détails du profil
    Informations personnelles :
    Âge : 43
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations forums :
    Inscription : Novembre 2004
    Messages : 53
    Par défaut
    le sizeof(tableau) si je ne me trompe pas te donne la taille d'un int soit 4.
    car faire sizeof(tableau) c'est comme faire sizeof(tableau[0]) soit la taille du premier element du tableau, soit la taille en memoire d'un entier.

    le sizeof est utilisé pour avoir la taille memoire la ce qu'on te demande c'est le nombre d'elements de ton tableau.

    ensuite le #define sert a definir la variable SIZE_TAB qui ser dans la fonction d'affichage de ton tableau et limite le nombre le nombre a SIZE_TAB ce qui est stupide.
    la fonction d'affichage affiche SIZE_TAB element quoi qu'il arrive alors que la taille de ton tableau peu etre variable.

  8. #8
    Expert éminent
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 395
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 41
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 395
    Par défaut
    SIZE_TAB est une constante, égal à 5.
    Partout où on utilise SIZE_TAB, on considère que c'est 5.

    Donc, si je fais ceci:
    Code C corrigé : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    void affiche_tab(int const *tab)
    {
    	size_t i;
    	for (i = 0; i < SIZE_TAB; i++)
    	{
    		printf (" %d ", tab[i]);
    	}
    }
    Cette fonction supposera toujours que le tableau a une taille de 5. Si on change SIZE_TAB, ça affectera toutes les fonctions qui l'utilisent.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  9. #9
    Membre émérite Avatar de orfix
    Homme Profil pro
    Inscrit en
    Avril 2007
    Messages
    707
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Maroc

    Informations professionnelles :
    Secteur : High Tech - Produits et services télécom et Internet

    Informations forums :
    Inscription : Avril 2007
    Messages : 707
    Par défaut
    Citation Envoyé par alaparra Voir le message
    le sizeof(tableau) si je ne me trompe pas te donne la taille d'un int soit 4.
    car faire sizeof(tableau) c'est comme faire sizeof(tableau[0]) soit la taille du premier element du tableau, soit la taille en memoire d'un entier.
    <...>
    Tu te trompe ...
    Citation Envoyé par §6.5.3.4 | ISO/IEC 9899:TC3
    The sizeof operator
    <...>
    When applied to an operand that has array type, the result is the total number of bytes in the array
    <...>

Discussions similaires

  1. Tri fusion avec seulement deux listes
    Par CrashBC dans le forum Algorithmes et structures de données
    Réponses: 1
    Dernier message: 04/01/2014, 01h02
  2. Requête absente pour fusion avec Word
    Par stéphane_ais2 dans le forum Access
    Réponses: 5
    Dernier message: 05/12/2006, 15h08
  3. tri dynamique avec XSLT
    Par JohnBlatt dans le forum XSL/XSLT/XPATH
    Réponses: 4
    Dernier message: 21/09/2005, 12h30
  4. [LG]Tri alphabetique avec les pointeurs
    Par zbooon dans le forum Langage
    Réponses: 4
    Dernier message: 06/03/2005, 17h04
  5. tri obligatoire avec DISTINCT?
    Par Marseillais9 dans le forum Langage SQL
    Réponses: 10
    Dernier message: 31/07/2003, 17h50

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo