2017-02-13 1 views
1

so habe ich diesen riesigen Haufen Code, aber es wird nicht richtig funktionieren. Und ich bin mir nicht sicher, wie eine Liste genau funktioniert. Kann mir jemand die richtige Richtung sagen, wer ist gut darin? Thanks so much :)Warum funktioniert meine doppelt verknüpfte Liste nicht? (Pascal)

Program ListendDerHoelle; 

Uses CRT; 

TYPE 
    Pokemon = ^pointer; 
    pointer = 
    RECORD 
     PokemonName : STRING[30]; 
     PokemonPosition : INTEGER; 
     Next : Pokemon; 
     Prev : Pokemon; 
    END; 
VAR Liste, Eintrag, head: Pokemon; 

FUNCTION TraverseList(AddPokemonPosition : INTEGER) : Boolean; FORWARD; 
PROCEDURE Ausgabe(i: Integer); FORWARD; 
PROCEDURE Abfrage; 
VAR PokemonName2 : STRING[30]; 
    PokemonPosition2, Anzahl, i : Integer; 

BEGIN 

    Liste := NIL; 
    Eintrag := NIL; 

    Anzahl := 99; 

    Writeln('Wie viele Pokemon einspeichern?'); 
    Writeln; 
    Readln(Anzahl); 

    FOR i := 1 TO Anzahl DO 
    BEGIN 
     ClrScr; 
     Writeln('Pokemon Name:'); 
     Writeln; 
     Readln(PokemonName2); 
     ClrScr; 
     Writeln('Pokemon Position:'); 
     Writeln; 
     Readln(PokemonPosition2); 
     ClrScr; 

     New(Eintrag); 
     Eintrag^.Next := NIL; 
     Eintrag^.Prev := NIL; 

     IF TraverseList(PokemonPosition2) = TRUE THEN 
     BEGIN 
       Eintrag^.PokemonName := PokemonName2; 
       Eintrag^.PokemonPosition := PokemonPosition2; 
       Liste := Eintrag; 
     END 
     ELSE 
     BEGIN 
      Writeln('Position nicht gefunden. Das Ende der Welt steht unmittelbar bevor!'); 
     END; 
    END; 

    Ausgabe(Anzahl); 


END; 
FUNCTION TraverseList(AddPokemonPosition : INTEGER) : Boolean; // Wenn die Funktion also True zurückgibt, ist das Element gefunden! 
VAR vElementFound : Boolean; 
BEGIN 

    vElementFound := FALSE; 
     TraverseList := FALSE; 


    WHILE (vElementFound = FALSE) DO 
    BEGIN 

        IF (Liste = NIL) THEN // wenn es das erste Element ist 
        BEGIN 
         vElementFound := TRUE; 
         Head := Liste; 
        END 

        ELSE IF ((Liste^.Next = NIL) AND (vElementFound = FALSE)) THEN  // wenn es das letzte Element ist 
        BEGIN 
         Liste := Liste^.Next; 
         vElementFound := TRUE; 
        END 
        ELSE IF (vElementFound = FALSE) THEN // ansonsten 
        BEGIN 
         IF (Eintrag^.PokemonPosition < AddPokemonPosition) AND NOT (Eintrag^.Next^.PokemonPosition > AddPokemonPosition) THEN 
         BEGIN 
           Liste := Liste^.Next; 
         END 
         ELSE IF (Eintrag^.PokemonPosition > AddPokemonPosition) AND NOT (Eintrag^.Prev^.PokemonPosition > AddPokemonPosition) THEN 
         BEGIN 
           Liste := Liste^.Prev; 
         END 
         ELSE 
         BEGIN 
          vElementFound := TRUE; 
         END; 
        END; 
    END; 

    IF (vElementFound = TRUE) THEN 
     BEGIN 
       TraverseList := TRUE; 
     END; 

END; 
PROCEDURE Ausgabe(i : Integer); 
var a : Integer; 
BEGIN 
     Liste := Head; 
     FOR a := 1 TO i DO BEGIN 


     Writeln(Eintrag^.PokemonName, ' ', Eintrag^.PokemonPosition); 
     Liste := Liste^.Next; 
     Readkey; 


     end; 


END; 



BEGIN 
Abfrage(); 
END. 

einfach das Endteil ignorieren, ich weiß, dass es wird nicht die richtigen Ergebnisse liefern noch, nur die Funktion „traverselist“ ist interessant

+0

Ihre Liste überschreibt jede Iteration, nicht wahr? – Emiliano

Antwort

1

Ich denke, Ihre TYPE Erklärung hat Sie bekam in ein hoffnungsloses Durcheinander. Das erste, was zu tun ist, das zu sortieren, und dann sollten Sie den Rest finden, ist sehr einfach.

Ich glaube, Sie werden die Einträge in verknüpften Liste beabsichtigen sein vom Typ Pokemon, aber es ist klarer, wenn Sie es ein PokemonNode aus Gründen nennen werde ich ..

nun erklären, eine einfach verkettete Liste ist eigentlich eine sehr einfache Struktur: Sie besteht aus einer Reihe von Knoten, die jeweils Datenfelder (in Ihrem Fall PokemonName und PokemonPosition) und einen Zeiger auf den nächsten Eintrag in der Liste enthalten.

Eine doppelt verknüpfte Liste ist wie eine einfach verknüpfte Liste, außer dass jeder Knoten auch einen Zeiger auf den vorherigen Knoten in der Liste sowie auf den nächsten hat.

Sie möchten also zwei Dinge definieren, einen PokemonNode, der ein einzelner Eintrag in der Liste ist, und einen PokemonPointer, der ein Zeiger ist, der auf einen Pokemon-Knoten zeigen kann. Die Art und Weise Sie diese in Pascal erklären ist wie folgt:

TYPE 
    PokemonPointer = ^PokemonNode; 
    PokemonNode = 
    RECORD 
     PokemonName : STRING[30]; 
     PokemonPosition : INTEGER; 
     Next : PokemonPointer; 
     Prev : PokemonPointer; 
    END; 

Btw, ich habe diese Namen gewählt, PokemonNode und PokemonPointer so dass, wenn Sie mit meinen Ihre TYPE Erklärung ersetzen, werden Sie durch den gesamten Code gehen müssen und ändern Sie es, aber noch wichtiger, so müssen Sie darüber nachdenken, was Sie mit dem Knoten und der Liste tun möchten.

Ich denke, dass Sie den Rest selbst machen können, aber wenn Sie stecken bleiben, fragen Sie. Bis Sie sich daran gewöhnt haben, über List-Knoten nachzudenken, könnte es hilfreich sein, Bilder zu zeichnen und zu beschriften, die das Erstellen + Einfügen eines neuen Knotens und das Entfernen eines solchen darstellen.

Ein Tipp, den Sie hilfreich finden können, ist Ihre Liste als eine kreisförmige schreiben (mit anderen Worten eine Next Zeiger des letzten Eintrags in der Liste auf den ersten Eintrag in der Liste. Dies vermeidet Ihren Code müssen Überprüfen Sie immer, ob der nächste Knoten Nil ist, bevor Sie etwas tun, sondern nur den Anfang der Liste verfolgen, indem Sie einen Zeiger darauf verwenden

+0

wow, super! Das ist eine großartige idee, ich werde es morgen ausprobieren! – user7285912

Verwandte Themen