[Übersetzerbau I] Fragen zu Typprüfung

Disclaimer: Dieser Thread wurde aus dem alten Forum importiert. Daher werden eventuell nicht alle Formatierungen richtig angezeigt. Der ursprüngliche Thread beginnt im zweiten Post dieses Threads.

[Übersetzerbau I] Fragen zu Typprüfung
Hallo,

ich hab da zwei Probleme beim Verständnis der Typprüfung (ab Folie 4-8).

  1. Streng getypt (Folie 4-8)
    Laut diversen Internetquellen ist Java eine streng typisierte Sprache. Nach unserer Definition [quote]
    Eine Sprache ist streng getypt, wenn ihre Übersetzer garantieren können, dass die akzeptierten Programme ohne Typfehler ablaufen werden.
    [/quote] ist Java aber meine ich nicht streng getypt. Ich kann doch bewusst lustige Casts einbauen, bei denen dann erst zur Laufzeit eine Exception fliegt - da ist der Compiler aber doch schon raus? Hab ich hier einen Denkfehler oder sind die verschiedenen Definitionen von “streng getypt” das Problem?

  2. Prototypen (ab Folie 4-17)
    Ich seh den Vorteil von Protoypen nicht. Laut Folien: “Prototyp ermöglicht genauere Fehlerpositionierung!” - aber das kann ich doch auch anders machen?

Mein bisheriges Verständnis: Situation wie in Folien: Zuweisung “x[sub]ref[/sub] := lit[sub]int[/sub]”.
-Ohne Prototypen: Typprüfung erfolgt im Zuweisungsknoten. Vorgehen: Rekursiver Abstieg nach x-Knoten um Typ zu bestimmen, dann rekursiver Abstieg in lit-Knoten um Typ zu bestimmen. Anschließend: Prüfen ob Typ von lit gleich dem x-Typ ist. Falls nicht: Fehler.
-Mit Prototypen: Typprüfung erfolgt im Knoten von lit. Vorgehen: Rekursiver Abstieg nach x-Knoten um Typ zu bestimmen, dann rekursiver Abstieg in lit-Knoten um Typ zu bestimmen und schauen, ob dieser Typ dem mitgegebenem Prototyp entspricht. Falls nicht: Fehler.

Aber: Ich weiß doch in beiden Fällen, welcher Typ erwartet wird und an welcher Stelle es kaputt geht. Ich kann doch auch ohne Prototyp sagen: “lit hat Typ int, es wird aber ‘Typ-von-x’ erwartet” (ich kenn ja beide Typen, sonst könnte ich sie ja nicht vergleichen!?).

Als weiteres Beispiel wird ein Funktionsaufruf angegeben, ohne Prototypen kann ich hier wohl nur sagen “Funktion wird falsch aufgerufen” - mit Prototypen kann ich sagen “Argument i hat falschen Typ”. Aber auch hier kann ich doch, wenn ich keine Prototypen habe, einfach die Argumente einzeln durchgehen und schauen welchen Typ ich hab bzw. was erwartet wird.

Interpretiere ich die Folien falsch? Auf Folie 4-18 steht dann noch, dass bei der Attributauswertung mit Prototypen keine reine Bottom-Up-Auswertung mehr erfolgt - versteh ich auch nicht, ich geh doch ganz genauso durch den Baum wie bei dem Fall “ohne Prototypen”? Oder ist’s jetzt keine “reine” Bottom-Up-Auswertung mehr, weil ich die Kindknoten jetzt streng von links nach rechts besuche, und diese Reihenfolge bei “normaler” Bottom-Up-Auswertung nicht vorgegeben ist?

Hat jemand ein paar Ideen für mich? Vielen Dank!



Und nebenbei gibts auch noch die Unterscheidung “dynamisch” und “statisch”, die sich auf den Zeitpunkt der Typpruefung bezieht. Damit koennte man Java als “streng” aber “dynamisch” oder “partiell dynamisch” klassifizieren, aber auch da gilt, dass die Grenzen fliessend und nicht exakt definiert sind.

Edit: Und die Definition von “Typfehler” kann man auch noch interpretieren: Wenn das Laufzeitsystem einen moeglichen Typfehler erkennt und per Exception behandelt, dann wurde ja eigentlich der Typfehler an sich nie realisiert sondern dessen Auftreten verhindert.


Zur 1)
Es gibt mehrere Definitionen zur Streng getypten sprachen. Die Definition aus der Vorlesung wuerde heissen, dass du keine Pointer in der Sprache hast, weil du mit Pointern/Referenzen immer irgendwas kaputtmachen kannst, was der Compiler einfach nicht sehen kann. Bei der Definition fehl auch: was genau ist ein Typfehler?

Zur 2)
Ich habe den Compiler in Python und Rekursiven Abstieg implementiert, genau so wie du es beschreiben hast. Vll geht es in Java mit den Besuchern nicht so, keine Ahnung.

Die Idee bei den Folien war, das der Knoten selbst entscheidet, ob er ein Typfehler hat. Was du gemacht hast ist ein spezieller Fall fuer das Assign statement, wo es selbst seine Unterknoten ABHAENGIG abprueft, oder?


Die interessante Frage ist: Was genau ist ein Typfehler?

Zählen die hier: Wat als Typfehler?
Zählen geworfene Exceptions als Typfehler?

Die Antwort ist… abhängig davon was der Autor des Textes dir verkaufen will :wink:

Und genau dieses „wird Typ-von-x erwartet“ wird in Form eines Prototypen mit runtergenommen.

Anders formuliert: Der Prototyp verbessert die Typprüfung, da beim Besuchen eines AST-Knoten nicht nur die Typinformation der (vorher besuchten) Kinder bekannt ist, sondern auch
(im Prototypen!) die Typinformation, die der Elternknoten erwartet.


Noch ein Beispiel, da ich mir selbst unsicher bin :slight_smile:

function calls

Hat eine Function mehrere Argumente, musst du ja in jedes Argument rein, wegen Typprüfung. Ein Argument knoten weiß aber nicht, zur welcher Funktion er gehört. Jetzt hast du 2 Möglichkeiten. Entweder prüft der Function call dann selber seine Argumente ab (was zu hässlichen Code führt, da plötzlich ein Knotentyp mit einer loop ausgestattet werden muss + Fehlermeldungen). Oder du machst es schön (Entwurfsmuster, yeah), und der Elternknoten (also der Funktioncall) gibt einen Prototypen an die jeweiligen Kinder (Argumente) weiter. Jedes Kind kann dann selber prüfen, ob es den richtigen Typ hat.

Das was vllt. verwirrend ist, dass die Typprüfung Bottom-up ist, aber die Prototypübergabe Top-down geschieht.