Comment feriez-vous ?

Sujets variés concernant le développement en PureBasic
Anonyme2
Messages : 3518
Inscription : jeu. 22/janv./2004 14:31
Localisation : Sourans

Comment feriez-vous ?

Message par Anonyme2 »

Bon,

Voilà le petit problème que je vous pose pour voir les différentes manières de faire.

On a une liste chainée basée sur une structure de disons 3 éléments.

Nom
Prenom
Age


Imaginons que nous ayons rempli cette liste chainée avec des élément, peu importe combien (5, 100, 10000 etc)
Comment feriez-vous pour supprimer chaque élément de la liste contenant le même prénom par exemple.
C'est pas une colle, c'est juste pour voir les différentes manières
T€r$@k€n
Messages : 42
Inscription : ven. 23/janv./2004 18:49

Message par T€r$@k€n »

Tu pourrais faire un tableau de type,
ensuite par une boucle for : next,
si Fiche(x)\Nom.s = "Tersaken" alors Fiche(x)\Nom.s = ""
Image
_______________________________________
Avatar de l’utilisateur
Chris
Messages : 3731
Inscription : sam. 24/janv./2004 14:54
Contact :

Message par Chris »

si Fiche(x)\Nom.s = "Tersaken" alors Fiche(x)\Nom.s = ""
... et tu te retrouves avec une fiche dont Fiche(x)\Nom.s est vide, mais la fiche est toujours là, avec le prénom, et l'age. Pas vraiment utile, d'après moi!

Fais plutôt DeleteElement(), ça t'enlève le nom, le prènom, et l'age, et ça te mets à jour les index.

Chris :)
comtois
Messages : 5186
Inscription : mer. 21/janv./2004 17:48
Contact :

Message par comtois »

si Fiche(x)\Nom.s = "Tersaken" alors Fiche(x)\Nom.s = ""
Si j'ai bien compris , il ne faut pas donner de prénom à l'avance , il s'agit de supprimer tous les éléments qui n'ont pas un prénom unique ?


Dans un bouquin sur le c , j'ai lu un truc qui s'apparente à ton problème .
Il s'agit de compter le nombre d'apparitions de chaque mot dans un fichier texte ( dans ton cas , ça pourrait être de chaque prénom ).
et la solution proposée utilise un arbre binaire pour classer les mots ( ou les prénoms ) .
une fois le classement fait , tu peux savoir quels sont les éléments de ta liste à supprimer car dans ton arbre tu sauras si un prénom est unique ou pas .

Car c'est bien de ça qu'il s'agit ? supprimer les doublons et plus ?


Les arbres ,on en a besoin pour de nombreuses choses ,depuis le temps que je me dis que c'est le sujet à bosser , je vais le faire cette fois ci :)
Dernière modification par comtois le ven. 26/mars/2004 21:38, modifié 2 fois.
T€r$@k€n
Messages : 42
Inscription : ven. 23/janv./2004 18:49

Message par T€r$@k€n »

Chris a écrit :
si Fiche(x)\Nom.s = "Tersaken" alors Fiche(x)\Nom.s = ""
si tu regardes un fichier texte vide, "" est la valeur ...
Image
_______________________________________
Avatar de l’utilisateur
Chris
Messages : 3731
Inscription : sam. 24/janv./2004 14:54
Contact :

Message par Chris »

Ben alors Denis, faudrait mieux expliquer :lol:

Parce que moi, ce que je comprends, c'est qu'il faut effacer tous les éléments qui contiennent le même prénom, donc, effacer aussi l'age, et le nom, et pas seulement le prénom!

Par exemple, en supposant que chaque élément de la liste (Nom + Prénom + Age) soit une fiche dans un agenda, il faut effacer la fiche.

C'est ça ???

Chris :)
Le Soldat Inconnu
Messages : 4312
Inscription : mer. 28/janv./2004 20:58
Localisation : Clermont ferrand OU Olsztyn
Contact :

Message par Le Soldat Inconnu »

ma première solution est de faire pour chaque element de la liste une recherche dans toute la liste pour savoir le même prénom existe et à chaque fois qu'il existe, on le supprime mais c'est plutot barabre.

en un peu mieux, j'ai de trier ta liste par prénom et ensuite de la parcourir en supprimant tous les éléments qui ont le même prénom que l'élément précédent. mais pour faire un trie, il faut d'abord recopier ton bazar dans une liste normal obtenu avec un Dim Liste.struturemachin(CountList())
Je ne suis pas à moitié Polonais mais ma moitié est polonaise ... Vous avez suivi ?

[Intel quad core Q9400 2.66mhz, ATI 4870, 4Go Ram, XP (x86) / 7 (x64)]
Avatar de l’utilisateur
Chris
Messages : 3731
Inscription : sam. 24/janv./2004 14:54
Contact :

Message par Chris »

Bon, ben moi, je pars sur mon idée, et tant pis si j'ai rien compris :lol:

Code : Tout sélectionner

;- Je commence par remplir la liste avec des datas, parce que ça va plus vite comme ça
Structure FICHE
  Nom.s
  Prenom.s
  Age.b ;<-- On pourrait mettre .w, mais faudrait que le mec arrive à 32767 ans :o))
EndStructure
NewList Agenda.FICHE()

Restore Noms              ;- Les noms
For i = 0 To 7
  AddElement(Agenda())
  Read Agenda()\Nom
Next

Restore Prenoms           ;- Les prénoms
For i = 0 To 7
  SelectElement(Agenda(),i)
  Read Agenda()\Prenom
Next

Restore Ages              ;- et les Ages
For i = 0 To 7
  SelectElement(Agenda(),i)
  Read Agenda()\Age
Next

;- Un petit coup de debug pour voir la liste complète
ForEach Agenda()
  Debug Agenda()\Nom + " " + Agenda()\Prenom + " = " + Str(Agenda()\Age) + " ans"
Next

Debug "--------------------------------------------"
Debug ""

;- On cherche les prénoms à supprimer : Jean et Jean-Philippe, mais pas Jean-René
ForEach Agenda()
  If Agenda()\Prenom = "Jean" Or Agenda()\Prenom = "Jean-Philippe"
    DeleteElement(Agenda())
  EndIf
Next
  
;- Encore un p'tit coup de debug pour la route
ForEach Agenda()
  Debug Agenda()\Nom + " " + Agenda()\Prenom + " = " + Str(Agenda()\Age) + " ans"
Next


DataSection

Noms:
Data.s "Lebrun", "Fernandez", "Duchmoll", "Martin", "Dupont", "Dupond", "Lefort", "Bernardeau"

Prenoms:
Data.s "Michel", "Jean-Philippe", "Bernard", "Michel", "Yannick", "André", "Jean-René", "Jean"

Ages:
Data.b 29,51,18,32,55,97,14,61

EndDataSection
Chris :)
Oliv
Messages : 2117
Inscription : mer. 21/janv./2004 18:39

Message par Oliv »

Moi je pensais tout simplement à regarder quand on met une nouvelle valeur si elle est identique à une valeur déjà connue :

Code : Tout sélectionner

Nom.s = "Monnom"
Prenom.s = "monprenom"
Adresse.s = "Maville"

ForEach Liste()
  If Liste()\Nom = Nom
    If Liste()\Prenom = Prenom
      If Liste()\Adresse = Adresse
        Debug "Il y a déjà ce nom"
        Break
      EnDif
    Endif
  Endif
  Addelement(Liste())
  Liste()\Nom = Nom
  Liste()\Prenom = Prenom
  Liste()\Adresse = Adresse
next
Je sais bien que tu as demandé si la liste est déjà faite mais quand il y a 5000 elements, la parcourir dans tous les sens prendrais des heures, alors que là on ne la parcour qu'une fois et de toute façon, il faut bien la créer la liste.
Anonyme2
Messages : 3518
Inscription : jeu. 22/janv./2004 14:31
Localisation : Sourans

Message par Anonyme2 »

Je vais mieux m'expliquer,

c'est ce que Chris a fait.

Donc par exemple si on a 10 éléments au total et que 4 on le meme prénom, on supprime ces 4 éléments, il doit donc en rester 6 qui ont un prénom différent de celui recherché.

Ce que Chris a fait c'est ce que je faisais, mais celà ne fonctionne pas corrrectement.

Voici la raison

La doc de DeleteElement dit ceci
Supprime l'élément courant de la liste spécifiée. Après l'appel de cette fonction, le nouvel élément courant est celui qui précédait l'élément supprimé. Si l'élément supprimé était le premier, alors l'élément suivant est selectionné (si il y en a un).
Donc si l'élément supprimé est le premier, alors l'élément suivant est selectionné (si il y en a un). Jusque là ça va.

Mais maintenant on reboucle et le foreach va sélectionner l'élément suivant et si celui en cours (donc le premier) contient également le prénom recherché il sera ignoré et ne sera pas effacé, donc cette façon ne va pas. On pourrait se dire que l'on teste ce nouvel élément mais on pourrait se retrouver dans ce cas.

J'utilise actuellement ceci

Code : Tout sélectionner

ForEach Agenda() 
    If Agenda()\Prenom = "Jean" Or Agenda()\Prenom = "Jean-Philippe" 
       DeleteElement(Agenda()) 
       Resetlist(Agenda())  ; --> on se remet au début de la liste et pas sur un élément
    endif
Next 
C'est bourrin mais je n'ai pas réfléchi plus que ça.

Un autre solution serait de modifier la fonction DeleteElement et ne pas la faire pointer sur l'élément suivant si c'est le premier élément.

Vous avez une autre solution ?
Oliv
Messages : 2117
Inscription : mer. 21/janv./2004 18:39

Message par Oliv »

T'as vu la mienne ? :cry: :cry:
Anonyme2
Messages : 3518
Inscription : jeu. 22/janv./2004 14:31
Localisation : Sourans

Message par Anonyme2 »

En fait olive, le problème n'est pas d'ajouter ou non l'élément mais de faire une recherche sur une valeur et de supprimer toutes les occurences dans la liste chainée.

J'ai été confronté à ce problèmedans ma librairie et je teste toujours pour voir si ca fonctionne et ça n'allait pas dans un cas précis.

Donc si vous trouvez une meilleur solution que la mienne, je prend. :D
Anonyme2
Messages : 3518
Inscription : jeu. 22/janv./2004 14:31
Localisation : Sourans

Message par Anonyme2 »

En fait la solution c'est de tester après le DeleteElement si l'élément est le premier et si oui on fait un resetlist.

Je viens seulement d'y penser :oops:
Fred
Site Admin
Messages : 2805
Inscription : mer. 21/janv./2004 11:03

Message par Fred »

Pour le DeleteElement(), je vais rajouter un flag pour les 2 modes différents d'operations, comme le suggere Denis.
brossden
Messages : 822
Inscription : lun. 26/janv./2004 14:37

Message par brossden »

Je vais surement défoncer une porte ouverte!
Mais le plus simple je crois, c'est de faire un tri de la liste par prénom.
Depuis le premier élement prendre le premier prénom comme référence.
Vérifier que le prénom suivant est différent :
si oui prendre ce nouveau prénom comme élément de comparaison.
sinon le détruire et vérifier avec le suivant
Ainsi de suite jusqu'à la fin de la liste !

Cela me parait tellement simple que j'ai du passé à coté du problème ! :roll: :roll: :roll:
Denis

Bonne Jounée à tous
Répondre