Einstein Rätsel in Prolog mit negation ?

Ausgehend von dem Beispiel auf dieser Seite:
http://www.logisch-gedacht.de/logikraetsel/einsteinr…

Habe ich versucht ein anderes Einstein Rätsel in Prolog zu Codieren worin auch Negationen wie „A sitzt NICHT neben B“ vorkommen.

Als Hilfsprädikate habe ich die gleichen verwendet die auch im angegebenen Link vorkommen. Also:

links(A,B,[A|[B|\_]]).
links(A,B,[_|R]):-links(A,B,R).
neben(A,B,L):-links(A,B,L);links(B,A,L).

Demnach habe ich Aussagen wie:
„Der Herr im Hemd saß nicht neben dem Herrn mit der Weste“

Codiert als:
neben([_,hemd,_],[_,not(weste),_],X),

Dies scheint zwar syntaktisch korrekt zu sein, da der Compiler keinen Fehler ausgibt, aber Logisch falsch da nur ein „false“ ausgegeben wird wenn es ausgeführt wird.

Wie ich die Negation „nicht neben“ anders darstellen könnte fällt mir leider nicht ein und ich bin mir auch nicht sicher ob ein einfaches not() dabei richtig ist. Kann mir vielleicht jemand weiterhelfen?

Den gesamten Code (25 Zeilen) gibt es hier:
http://uploaded.to/file/ezjmoh

ANTWORT. prolog IST NICHT DIE PRÄDIKATENLOGIK!!! UND HAT KEINE QUANTOREN ODER EINE NEGATION!!! NUR WEGEN DES CLOSED-WORLD APPROCHES KANN EINE NICHT ERÜLLBARE KLAUSE ALS NEGATION INTERPRETIERT WERDEN. iCH BIN leider nicht mehr ganz up-to-date, weil ich seit 2 jahren krank bin und nicht mehr unterrichten kann an der tu-wien. die antwort false heisst wie sie sicher wissen, dass er nicht matchen konnte: entweder sind die vorgegebenen sätze nicht zusammen erfüllbar, oder es ist ein programmfehler. PROLOG-programme sind sehr schwer zu entbugen, weil es keine compiler gibt.Mein Tipp: lösen sie lieber die Gödel-Rätsel in Smullians"Wie heist dieses Burätseln schläft man ja ein.

Hi MiB,
das ist nicht so einfach, wie die letzte Frage …

Ich würde sogar sagen DENKFEHLER.

Prolog, also Prädikatenlogik, kennt eigentlich nur
„positive“ Beweise.

Wenn „true“ bzw. YES herauskommt, wurde das Goal
bewiesen. Aber bei „fail“ ist das nicht so klar:
Es gibt dann grundsätzlich 2(!) Möglichkeiten.
Entweder wurde z.B. unter Verwendung von not(_)
oder einem !,fail tatsächlich gezeigt, dass etwas
nicht zutrifft, ODER es wurde einfach kein Weg
gefunden, das Goal zu verifizieren.
Das bedeutet in etwa, für Prolog sind die Aussagen
„falsch“ und „ich weiss nicht“ gleichermassen ein
fail.

Aussagen wie „A sitzt neben B“ beziehen sich damit
nicht auf die Tatsache, wer neben wem sitzt, sondern
darauf, ob genug Fakten vorliegen, dies auch zu
zeigen. Wenn nich genug Fakten vorliegen, wird Prolog
für „A sitzt neben B“ ein fail i.e. false antworten,
auch wenn die doch nebeneinader sitzen.
-> Aus „ich weiss nicht“ wird somit ein FALSCH.

Und damit funktionieren die von Dir eingeführten
not(Aussagen) nicht, da aus Not(„ich weiss nicht“)
ein True wird. Das führt in´s logisch Chaos.
Alles, was er nicht weiss wird plötzlich wahr …

Du musst Dir mal Beispiele suchen, wie solche Probleme
formuliert werden können.
Um beim Beispiel zu bleiben: Meisstens wird ausser
der Eigenschaft „sitzt neben“ eine zweite Eigenschaft „sitzt nicht neben“ definiert und dann kann „positiv“
danach gesucht werden.
not wird dann soweit nötig erst ganz am Schluss
verwendet, wenn die Eigenschaften „sitzt neben“ oder
„sitzt nicht neben“ bereits besttimmt wurden …

PrädikatenLogik mit Negationen ist leider nicht trivial.

P.S.: beschäftigst Du Dich einfach so damit, oder
ist das Schule / FH / Uni Kontext ?
Würde mich interessieren, wo Prolog noch unterrichtet wird …

Gruss,
Thilo

Ja, Prolog wird an der FH im Fach „Einführung in die Künstliche Intelligenz“ unterrichtet… Es würde mir schon weiterhelfen zu wissen ob überhaupt ein „not()“ die richtige vorgehensweise ist negative aussagen zu formulieren.

Das „not(X)“ in Prolog bedeutet „Aussage X kann nicht abgeleitet werden“. Hier mal ein minimales Rätsel: Es gibt Honda- und BMW-Fahrer. BMW-Fahrer essen Äpfel und Bananen. Honda-Fahrer essen nur Äpfel. A isst nie Bananen. Was fährt A?


auto(bmw).
auto(honda).

isst(bmw, apfel).
isst(bmw, banane).
isst(honda, apfel).

run :- auto(A),
not(isst(A, banane)),
write(A).


In „run“ wird durch den Aufruf von „auto(A)“ eine Fallunterscheidung (bmw oder honda) in Gang gesetzt. Würde „run“ so aussehen:

run :- not(isst(A, banane)),
auto(A),
write(A).

dann würde das Programm nicht funktionieren, weil isst(A, banane) erfüllbar ist, und somit not(isst(A, banane)) fehlschlägt, ohne dass andere Fälle probiert würden.

Antwort: Ich habe folgendes getestet:

links(gerd,gerda,paul).
links(A,B,[A,B|_]).
links[A,B,[_|R]):-links(A,B,R).
Die obige Datei liefert
nach links(gerd,_,_). ein Yes, weil der Fakt vorhanden ist.
Auf die frage ?- links(gerd,X,Y). kommt die Antwort X = gerda,
Y = paul.

Auf die frage ?- links(gerda ,X,Y). kommt die Antwort
Y = [gerda, X|_G370] ;
No
Es könnte also an den Fakten bzw. an den fehlenden Variablen X und Y liegen. Um genauer zu antworten, brauche ich mehr von den Regeln und Fakten.

Es fällt mir auch gerade ein fehler im code auf. Fakt nr. 15 und 16 ist gleich. Nr. 16 wurde nun korrigiert aber da tritt auch das gleiche problem auf das ich bei nr. 11 hatte. Ich weiß nicht was ich mit barhocker nummern anfangen kann.

Hier ist die Komplette Fragestellung:
http://a.imageshack.us/img440/327/cimg1447w.jpg

Und hier der korrigierte Code:
http://uploaded.to/file/el2o81

Ein sehr ähnliches Beispiel gibt es unter folgender URL:
http://www.hajoinbergen.de/Aufgabe2.htm