2017-03-27 3 views
1

Ich habe einen Operator # definiert:Wie kann ich einen Syntaxfehler in Prolog abfangen?

:- op(500, yfx, #). 

ich die folgenden Regeln geschrieben haben zu prüfen, ob ein Begriff wohlgeformt ist:

valid(X):- integer(X). 
valid(X # Y):- valid(X), valid(Y). 

ich ein Prädikat check/1 schreiben wollen, die wahre zurückkehren wenn das Argument gültig ist und andernfalls falsch. Ich schrieb dies:

check(Exp):- catch(valid(Exp), error(syntax_error(_),_), fail), !. 

Es gibt wahr, wenn Exp ist wohlgeformt. Allerdings ist es nicht die Syntaxfehler fangen, wenn es nicht legal:

?- check(5 ## 6). 
ERROR: [Thread pdt_console_client_0_Default Process] Syntax error: Operator expected 
ERROR: [Thread pdt_console_client_0_Default Process] check(5 
ERROR: [Thread pdt_console_client_0_Default Process] ** here ** 
ERROR: [Thread pdt_console_client_0_Default Process] ## 6) . 

ich SWI-Prolog version 7.4.1 for amd64 verwende.

Wie kann ich den Syntaxfehler abfangen und check false zurückgeben, wenn ein Fehler ausgelöst wird?

Antwort

3

In Ihrem Fall ist das Problem, dass check/1 nur aufgerufen, wenn ein gültiges Prolog Ziel in dem ersten   Ort eingegeben wird.

Wenn also check/1 bereits aufgerufen wird, ist die Syntax auf jeden Fall zumindest ein gültiger Prolog   Begriff, auch wenn es nicht sinnvoll, aus der Sicht von check/1 selbst machen kann. Wenn die Syntax nicht   gültig ist, der Prolog   Toplevel schon wirft eine   Fehler, ohne auch nur   check/1 aufrufen.

Daher für mehr Kontrolle über Syntaxprobleme, müssen Sie lesen Sie die Begriffe selbst.

Es gibt mehrere Möglichkeiten, dies zu tun. Ein einfacher ist zu verwenden read/1. Zum Beispiel:

 
?- catch(read(X), Error, true). 
|: check(5##6). 

Error = error(syntax_error(operator_expected), stream(user_input, 8, 7, 347)). 

Auf diese Weise können Sie im Wesentlichen Ihre eigenen Top-Level bauen, die Ihnen mehr Kontrolle über solche   Probleme gibt. Siehe auch read_term/2 und mehrere verwandte Prädikate, die dabei helfen.

Eine wichtige Option im Zusammenhang mit solchen Fragen ist variable_names/1: Es ergibt sich eine Übereinstimmung zwischen Prolog   Variablen und deren Atom Namen, so dass Sie lesbar   Bindungen mitteilen. Dies ist ein entscheidender Teil des Toplevels, und jüngste Fortschritte bei der ISO-Standardisierung haben bei solchen Funktionen enorm geholfen. Vielleicht können wir zu gegebener Zeit tragbare Top-Level in   Prolog schreiben, verwendbar in mehreren   Systemen. Es gibt viele Anwendungen, die davon profitieren würden, da Sie einer davon sind.

Verwandte Themen