Autor |
Beitrag |
Torsten
Beiträge: 160
|
Verfasst: Di 01.10.02 19:48
Moinsen Leute!
Mal eine elementare Frage zu Pascal.
Ich habe den ganzen Sommer über keinen Rechner gesehen, also viel vergessen. Besonders, was reines Pascal angeht.
Also, ich will in einem kleinen Programm das Skalar-Produkt im n-dimensionalen Raum berechnen.
Die eigentliche Berechnung ist mir eigentlich klar, nur die Arrays gefallen mir nicht so recht.
Ich kann euch ja mal meinen Entwurf zeigen.
Zu beachten ist noch, dass das Skalarprodukt später mittels "s:=Skal_Prod(n, V, W)" aufgerufen werden soll.
n ist also die Dimension (2,3,4,...) und V bzw. W die Vektoren.
Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20:
| program skalar;
function Skal_Prod(n:Integer; x:array of Real; y:array of Real):Real; var i: Integer;
begin i:=1; Skal_Prod:=0.0;
repeat Skal_Prod:=Skal_Prod + (x[i]*y[i]); i:=i+1; until i > n; end;
begin // ab hier nun das Hauptprogramm end. |
Nun noch eine Fragen.
In Zeile "Skal_Prod:=Skal_Prod + (x[i]*y[i]);" bekomme ich einen Compiler-Fehler!
Wieso? Geht das so nicht?
Ach ja, hat jemand rein zufällig ein gutes Forum für reines Pascal in Verbindung mit Mathe?
Fragende Grüße
Torsten
|
|
Christian S.
Beiträge: 20451
Erhaltene Danke: 2264
Win 10
C# (VS 2019)
|
Verfasst: Di 01.10.02 19:54
Hi!
Pascal ist bei mir jetzt schon 3 Jahre her, aber mit einer Function darfst Du in Pascal glaube ich keine solche Zuweisung machen. Definiere Dir doch eine lokale Variable vom Typ Real, mit der Du die gleichen Berechnungen machst, die Du aber erst ganz am Ende Skal_Prod zuweist.
Bei Delphi fangen Arrays, wie Du sie verwendest, mit dem Index 0 an, ist das bei Pascal anders?
MfG,
Peter
_________________ Zwei Worte werden Dir im Leben viele Türen öffnen - "ziehen" und "drücken".
|
|
Torsten
Beiträge: 160
|
Verfasst: Di 01.10.02 19:59
Hallo!
OK, das mit der Variablen habe ich mir auch überlegt. Ich war jedoch der Meinung, dass es auch so geht. aber man lernt ja immer dazu.
Tja, Arrays in Pascal. Ich denke mal auch, dass sie bei 0 beginnen. Also ähnlich C oder Delphi. Sicher bin ich mir jedoch auch nicht, daher die Frage.
Kann man den ganzen Kram nicht ohnehin irgendwie besser machen?
Grüße
Torsten
|
|
Christian S.
Beiträge: 20451
Erhaltene Danke: 2264
Win 10
C# (VS 2019)
|
Verfasst: Di 01.10.02 20:07
Hi!
Ich glaube nicht, dass man das ganze noch verbessern kann. Die Laufzeit ist glaube ich mit einer linearen Abhängigkeit von n ganz in Ordnung. Man kann natürlich jetzt versuchen, herauszufinden, ob Inc(i) schneller ausgeführt wird als i:=i+1; aber ganz ehrlich halte ich das für maßlos übertrieben.
MfG,
Peter
P.S.: Definiere doch alle Winkel als 90°, dann ist das Skalarprodukt ganz einfach Null!
_________________ Zwei Worte werden Dir im Leben viele Türen öffnen - "ziehen" und "drücken".
|
|
Klabautermann
Beiträge: 6366
Erhaltene Danke: 60
Windows 7, Ubuntu
Delphi 7 Prof.
|
Verfasst: Di 01.10.02 20:33
Hallo,
Torsten hat folgendes geschrieben: |
Quelltext 1:
| Skal_Prod:=Skal_Prod + (x[i]*y[i]); |
|
Skal_Prod ist deine funktion, also ist der erste Teil der Zeile (Skal_Prod:=) Ok. Danch rufst du aber wieder Skal_Prod auf. Das währe generell auch kein Problem, nur müsstest du dann:
1. auch die benötigten Parameter übergeben.
2. Eine abbruchbedingung für die benötigte Rekursion schreiben.
Ich glaube aber nicht, das du überhaupt eine Rekursion machen willst.
Wenn du das ganze in Delphi Implementierst, kannst du Result verwenden (ich weis nicht mit welcher Verion das eingeführt wurde, vieleicht gab es das schon in neueren Turbo Pascal Versionen).
Dann sähe deine Funktion so aus:
Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11:
| function Skal_Prod(n:Integer; x:array of Real; y:array of Real):Real; var i: Integer; begin i:=1; Result:=0.0; repeat Result:=Result + (x[i]*y[i]); i:=i+1; until i > n; end; |
Ansonsten musst du tatsächlich zu einer Hilfsvariable greifen.
Mit freundlichen Grüßen
Klabautermann
|
|
Torsten
Beiträge: 160
|
Verfasst: Di 01.10.02 21:09
Moinsen!
Besten Dank für die Antworten.
Ja, result kenne ich von Delphi auch. Aber eben nicht unter Pascal. Und da bin ich schon seit bestimmt 10 Jahren raus (habe auch nicht viel mit gearbeitet).
Habe es aber eben getestet.
Ich arbeite mit GnuPascal unter Linux.
result scheint auch hier zu funktionieren.
Um es aber auch für andere Compiler zu schreiben, werde ich eine globale Variable verwenden.
Grüße
Torsten
|
|
Christian S.
Beiträge: 20451
Erhaltene Danke: 2264
Win 10
C# (VS 2019)
|
Verfasst: Di 01.10.02 21:35
Eine globale Variable?
_________________ Zwei Worte werden Dir im Leben viele Türen öffnen - "ziehen" und "drücken".
|
|
Torsten
Beiträge: 160
|
Verfasst: Di 01.10.02 21:43
Sorry, falsch ausgedrückt.
Gilt natürlich nur für die Funktion.
Ich habe aber wieder ein anderes Problem.
Und zwar mit einem dynamischen Array.
So, mal eben das Programm:
Quelltext 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:
| program skalar; var i: Integer; n: Integer; v,w: array of Real;
{die eigentliche Funktion} function Skal_Prod(n:Integer; x:array of Real; y:array of Real):Real; var i: Integer; result: Real;
begin i:=1; result:=0.0;
repeat result:=result + (x[i]*y[i]); i:=i+1; until i > n; return result; end;
{ eigentliches Hauptprogramm } begin writeln('Das Skalarprodukt:'); // s:=Skal_Prod(......) end. |
Der Compiler meldet in der 5. Zeile bei
"v,w: array of Real;"
einen Fehler (parse error befor 'of')
Hö?
Wieso?
Dynamische Arrays gibt es doch bei Pascal.
Grüße
Torsten
|
|
Christian S.
Beiträge: 20451
Erhaltene Danke: 2264
Win 10
C# (VS 2019)
|
Verfasst: Di 01.10.02 22:14
Hi!
Ich habe jetzt nochmal mein altes TP7 herausgekramt und bei dem Code, den Du verwendest, meckert er. Anscheinend kannst Du Arrays ohne Größenangabe nur als Parameter übergeben. Aber als ich TP programmiert habe, war ich noch nicht so weit, dass ich überhaupt auf die Idee von dynamischen Arrasy gekommen wäre; also kann es sein, dass es da irgendeinen Code gibt, wie man sie doch verwenden kann.
MfG,
Peter
P.S.: Die Fehlermeldung bei mir: "[" oder "(." erwartet
_________________ Zwei Worte werden Dir im Leben viele Türen öffnen - "ziehen" und "drücken".
|
|
Torsten
Beiträge: 160
|
Verfasst: Di 01.10.02 22:20
Moinsen!
Verdammte Axt.
Anscheinend gibt es doch keine dynamischen Arrays.
Eben doch nur als Parametrübergabe.
Naja, dann muss ich mir was einfallen lassen.
Dumm ist nur, dass ich die dort gebrauchen könnte.
Denn man weiss ja vorher nicht, in welcher Dimension das das Skalarprodukt gebildet werden soll.
Grüße
Torsten
|
|
Christian S.
Beiträge: 20451
Erhaltene Danke: 2264
Win 10
C# (VS 2019)
|
Verfasst: Di 01.10.02 22:34
Hi!
Könntest Du das ganze nicht als Records in temporären Dateien speichern? Die kannst Du beliebig groß machen. Ist zwar ein Algorithmus mit der Brechstange aber es könnte funktionieren!
MfG,
Peter
_________________ Zwei Worte werden Dir im Leben viele Türen öffnen - "ziehen" und "drücken".
|
|
CenBells
Beiträge: 1547
Win 7
Delphi XE5 Pro
|
Verfasst: Di 01.10.02 22:39
Zitat: | Ich glaube nicht, dass man das ganze noch verbessern kann. Die Laufzeit ist glaube ich mit einer linearen Abhängigkeit von n ganz in Ordnung. Man kann natürlich jetzt versuchen, herauszufinden, ob Inc(i) schneller ausgeführt wird als i:=i+1; aber ganz ehrlich halte ich das für maßlos übertrieben. |
Inc(i) wird schneller ausgeführt, als i := i+1;
Gruß
Ken
|
|
Torsten
Beiträge: 160
|
Verfasst: Di 01.10.02 22:40
Hui, das wäre mir dann doch zu viel.
Es war eigentlich nur ein Test.
Ich habe nämlich gerade in einem alten Pascal-Buch gestöbert.
Dort stand die Aufgabe, dass man eine Funktion entwickeln soll, die das Skalarprodukt errechnet.
Diese Funktion sollte dann mit Wertübergabe aufgerufen werden. Aber das drumherum war weniger interessant.
Ich wollte es dennoch gerne probieren (ohne Erfolg).
Grüße
Torsten
|
|
Christian S.
Beiträge: 20451
Erhaltene Danke: 2264
Win 10
C# (VS 2019)
|
Verfasst: Di 01.10.02 22:52
Ireniceus hat folgendes geschrieben: |
Inc(i) wird schneller ausgeführt, als i := i+1;
|
Hatte ich schon vermutet, ansonsten würde es kaum Sinn machen, eine solche Funktion zu implementieren.
MfG,
Peter
_________________ Zwei Worte werden Dir im Leben viele Türen öffnen - "ziehen" und "drücken".
|
|
Torsten
Beiträge: 160
|
Verfasst: Di 01.10.02 23:00
Moinsen!
Nochmal zum dynamischen Array.
In C wüsste ich, wie zu implementieren (malloc).
Auch in Delphi.
Nur eben nicht in Pascal.
Aber: Man kann das auch als verkette Liste ausführen.
Doch ich will mal nicht übertreiben.
Außer jemand hat einen einfachen, genialen Vorschlag.
Grüße
Torsten
|
|
Klabautermann
Beiträge: 6366
Erhaltene Danke: 60
Windows 7, Ubuntu
Delphi 7 Prof.
|
Verfasst: Di 01.10.02 23:11
Hallo!
Was ist an der Verketteten liste so schlim?
|
|
Torsten
Beiträge: 160
|
Verfasst: Di 01.10.02 23:46
Moinsen!
Och naja, irgendwie sträube ich mich immer etwas dagegen.
Hast Du etwa eine Lösung für meine Aufgabe?
Grüße
Torsten
|
|
Klabautermann
Beiträge: 6366
Erhaltene Danke: 60
Windows 7, Ubuntu
Delphi 7 Prof.
|
Verfasst: Mi 02.10.02 01:00
Hallo,
da verlangst du was zu dieser späten Stunde. Aber gut, dann werde ich mal schnell was hintippen.
Aber eins vorweg: Aufgrund der vortgeschrittenden Zeit habe ich das nicht getestet oder nochmal genauer überprüft. Wenn es ein Problem gibt können wir Morgen nochmal drüber reden:
Also hier die Datentypen:
Delphi-Quelltext 1: 2: 3: 4: 5: 6:
| TYPE pRealList = ^tRealList; tRealList = PACKED RECORD Value : Real; Next : pRealList; END; |
Die Variablendeklaration:
Delphi-Quelltext 1: 2:
| VAR v, w : pRealList; |
Vergiss die Initialisierung nicht:
Delphi-Quelltext
Und das Werkzeug:
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:
| procedure Appent2RealList(Value : Real; aList : pRealList); VAR Runner, NewEle : pRealList; BEGIN NEW(NewEle); NewEle^.Value := Value; NewEle.Next := NIL; Runner := aList; IF (Runner = NIL) THEN aList := NewEle ELSE BEGIN WHILE (Runner^.Next <> NIL) DO Runner := Runner^.Next; Runner^.Next := NewEle; END; END; function RealListLength(aList : pRealList) : LongInt; VAR Runner : pRealList; BEGIN Result := 0; Runner := aList; WHILE (Runner <> NIL) DO BEGIN INC(Result); Runner := Runner^.Next; END; END; function GetRealValue(aIndex : LongInt; aList : pRealList) : Real; VAR Runner : pRealList; i : LongInt; BEGIN Result := 0; IF (aIndex < RealListLength(aList)) THEN BEGIN Runner := aList; FOR i := 1 TO aIndex DO Runner := Runner^.Next; Result := Runner^.Value; END; END; procedure RemoveRealValue(aIndex : LongInt; aList : pRealList); VAR Runner, tmp : pRealList; i : LongInt; BEGIN IF (aIndex < RealListLength(aList)) THEN BEGIN Runner := aList; IF (aIndex = 1) THEN BEGIN tmp := Runner; aList := aList^.Next; END ELSE BEGIN FOR i := 1 TO aIndex - 1 DO Runner := Runner^.Next; tmp := Runner^.Next; Runner^.Next := Runner^.Next^.Next; END; Dispose(tmp); END; END; procedure ClearRealList(aList : pRealList); VAR tmp : pRealList; BEGIN WHILE (aList <> NIL) DO BEGIN tmp := aList; aList := aList.Next; Dispose(tmp); END; END; |
Und jetzt mach' was draus .
Gruß
Klabautermann
Zuletzt bearbeitet von Klabautermann am Di 17.06.03 10:38, insgesamt 1-mal bearbeitet
|
|
Torsten
Beiträge: 160
|
Verfasst: Mi 02.10.02 09:12
Moinsen!
Na hossa, das schaut ja wirklich gut aus.
Dennoch mag ich keine Listen, geschweige denn verkette Listen.
Aber bei Deinem Code sehe ich gut durch. Ist auch alles wunderbar enthalten (insert, remove, Länge,..)
Eigentlich wollte ich ja nicht so weit mit meinem Problem gehen, doch eventuell findet sich etwas Zeit.
Besten Dank dafür.
Grüße
Torsten
|
|
Klabautermann
Beiträge: 6366
Erhaltene Danke: 60
Windows 7, Ubuntu
Delphi 7 Prof.
|
Verfasst: Mi 02.10.02 16:00
Hallo,
Torsten hat folgendes geschrieben: | Dennoch mag ich keine Listen, geschweige denn verkette Listen. |
das ist schade, sie sind sehr Praktisch und im Klassischen Pascal der Standard-Weg für Dynamische Speicherverwaltung. Mann muss sich nur einmal richtig damit auseinander setzen, dann verlieren sie ihren Schrecken.
Torsten hat folgendes geschrieben: | Aber bei Deinem Code sehe ich gut durch. Ist auch alles wunderbar enthalten (insert, remove, Länge,..) |
Ja, wenn man sich am Anfang ein wenig Arbeit macht, kann man später sehr konfortabel Arbeiten und hat auch keine sorgen mehr mit den Verketteten listen .
Torsten hat folgendes geschrieben: | Eigentlich wollte ich ja nicht so weit mit meinem Problem gehen, doch eventuell findet sich etwas Zeit. |
Ich zwinge dich ja nicht. Wie gesagt, wenn es dir hilft, dann viel Spass damit. Wenn nicht, vieleicht lernt ein mitleser was draus .
Torsten hat folgendes geschrieben: | Besten Dank dafür. |
Bitteschön, ich hatte Spaß dabei, denn heutzutage kommt man ja nicht mehr so oft dazu (denn Dynamische Arrays oder tList finde ich auch schnuckelig und verwende sie daher).
Gruß
Klabautermann
|
|