Bonjour , le 11 octobre 2008 :D
voila je vous propose une solution qui consiste à réaliser une fonction qui reçoit l'adresse d'une liste et divise cette liste en deux sous listes, en utilisant une autre fonction qui calcule la taille d'une liste simple circulaire:
cette fonction retourne l'adresse de la 1ere sous liste;
et l'adresse de la 2eme sous liste , c'est l'adresse de la liste initiale càd l'adresse reçu en paramètre voila un exemple pour mieux comprendre:
L1=diviser_2(&lst);
printf("\n\n\n les éléments de la première liste : "); afficher(L1);
printf("\n\n la taille de la première liste est : %d",lenght(L1));
printf("\n\n\n les éléments de la deuxième liste : "); afficher(lst);
printf("\n\n la taille de la deuxième liste est : %d",lenght(lst));
lst : c'est la liste qu'on veut diviser.
diviser_2(&lst); divise la liste en deux , et retourne l'adresse de la 1ere sous liste.
L1 : c'est l'adresse de la 1ere liste.
lst : maintenant lst contient l'adresse de la 2eme liste
lst : 1->2->3->4->5->6
diviser_2(&lst);
L1 : 1->2->3
lst : 4->5->6
liste diviser_2(liste *L)
{int taille=lenght(*L);// la taille de la liste
int NbrL1=0; // une variable qui calcule à chaque fois le nombre d'élément de la 1ere sous liste
liste parcourir = *L , adr_L1 = *L , sauv;
if(parcourir)// tester d'abord si la liste n'est pas vide
{while(parcourir = parcourir->suiv , NbrL1++ , NbrL1 < (taille/2) );
adr_L1 = parcourir; // l'adresse de la 1ere liste
sauv = parcourir->suiv; // si on sauvegarde pas cette adresse on risque de la perdre en découpant
parcourir->suiv = (*L)->suiv ;// on fait le chainage de la 1ere sous liste
(*L)->suiv = sauv; // on relie l'ancienne liste avec le nouveau élément
}
return adr_L1;
}
NB : si on fait pas le test if(parcourir) càd if(parcourir != NULL)
si jamais la liste est vide càd lst=NULL alors parcourir = NULL, donc si on fait pas ce test alors on va passé à la boucle while , après lors de l'exécution de parcourir = parcourir->suiv le programme s'arrête ERREUR car parcourir == NULL donc parcourir->suiv n'a pas de sens .
pour la fonction qui retourne la taille d'une liste circulaire :
int lenght(liste lst)
{liste p=lst; int l=0;
if(p)while(p=p->suiv,l++,p!=lst);
return l;
}
pour tester cette fonction voila un programme :
prog.cpp
//****************** Ouadie Boussaid 2°IIR3 EMSI****************************
#include<stdio.h>
#include<conio.h>
#include<string.h>
#include<stdlib.h>
typedef int typeElem;
typedef struct noeud
{ typeElem val;
struct noeud *suiv;
};
typedef struct noeud* liste;
liste remplir()
{liste L=NULL,;
struct noeud *nouv,*der=NULL;
typeElem val;
printf("\n donner les valeurs de la liste (0 pour sortir) : ");
scanf("%d",&val);
if(val){
nouv=(noeud*)malloc(sizeof(struct noeud));
L=nouv;
der=nouv;
nouv->val=val;
nouv->suiv=L;
while(scanf("%d",&val), val!=0
&& ( nouv=(noeud*)malloc(sizeof(struct noeud)) ))
{
nouv->val=val;
nouv->suiv=L;
der->suiv=nouv;
der=nouv;
}}
return der;
}
int lenght(liste lst)
{liste p=lst; int l=0;
if(p)while(p=p->suiv,l++,p!=lst);
return l;
}
liste diviser_2(liste *L)
{int taille=lenght(*L);// la taille de la liste
int NbrL1=0; // une variable qui calcule à chaque fois le nombre d'élément de la 1ere sous liste
liste parcourir = *L , adr_L1 = *L , sauv;
if(parcourir)// tester d'abord si la liste n'est pas vide
{while(parcourir = parcourir->suiv , NbrL1++ , NbrL1 < (taille/2) );
adr_L1 = parcourir; // l'adresse de la 1ere liste
sauv = parcourir->suiv; // si on sauvegarde pas cette adresse on risque de la perdre en découpant
parcourir->suiv = (*L)->suiv ;// on fait le chainage de la 1ere sous liste
(*L)->suiv = sauv; // on relie l'ancienne liste avec le nouveau élément
}
return adr_L1;
}
void afficher(liste lst)
{liste p=lst;
if(p)while(p=p->suiv,printf("%d->",p->val),p!=lst);
}
main()
{liste lst,L1; int x;
lst=remplir();
printf("\n les éléments de la liste : ");
afficher(lst);
printf("\n\n la taille de la liste est : %d",lenght(lst));
L1=diviser_2(&lst);
printf("\n\n\n les éléments de la première liste : ");
afficher(L1);
printf("\n\n la taille de la première liste est : %d",lenght(L1));
printf("\n\n\n les éléments de la première liste : ");
afficher(lst);
printf("\n\n la taille de la première liste est : %d",lenght(lst));
getch(); }
///********************************************
===========
Deux choses sont infinies : l’Univers et la bêtise d'Albert Einstein. Mais, je ne sais pas laquelle est arrivée en premier.