Логическая задача Prolog - Prolog (226274)

Формулировка задачи:

Помогите, пожалуйста, решить логическую задачу.
Болельщики футбольных команд делали прогнозы об итогах соревнований «Турнир четырех»: — Я уверен, что Спартак будет чемпионом, а ЦСКА займет последнее место — сказал Иван. — Что ты, Спартак выше третьего не поднимется, а ЦСКА станет вторым — возразил Сергей. — Чемпионом будет Динамо, а ЦСКА войдет в тройку сильнейших — сделал свой прогноз Петр. — Динамо будет вторым, а вот Ротор точно будет последним — промолвил Алексей. Выяснилось, что каждый из болельщиков был прав в одном прогнозе и ошибся во втором. Как распределились места, занятые командами?
Проблема в том, что нужно и учесть условие "каждый из болельщиков был прав в одном прогнозе и ошибся во втором" и установить между названием команды-местом взаимнооднозначное соответствие. Добавлял объекты для обозначения различных болельщиков, чтобы условие учесть, но тогда соответствия нет, и выводятся лишние варианты. В итоге додумался только сгруппировать в утверждениях условия для каждой команды, но это, очевидно, просто перебор всех вариантов с такими условиями:
PREDICATES
nondeterm соответствие(string, integer)
nondeterm название(string)
nondeterm место(integer)
nondeterm решение(string, string, string, string, integer, integer, integer, integer)
 
CLAUSES
название("ЦСКА").
название("Спартак").
название("Динамо").
название("Ротор").
 
место(1).
место(2).
место(3).
место(4).
 
соответствие(X, Y) :- название(X), X = "Спартак", место(Y), Y = 1; название(X), X = "Спартак", место(Y), not(Y = 1), not(Y = 2).
соответствие(X, Y) :- название(X), X = "ЦСКА", место(Y), Y = 2; название(X), X = "ЦСКА", место(Y), Y = 4; название(X), X = "ЦСКА", место(Y), not(Y = 4).
соответствие(X, Y) :- название(X), X = "Динамо", место(Y), Y = 1; название(X), X = "Динамо", место(Y), Y = 2; название(X), X = "Динамо", место(Y), not(Y = 2), not(Y = 1).
соответствие(X, Y) :- название(X), X = "Ротор", место(Y), Y = 4; название(X), X = "Ротор", место(Y), not(Y = 4).
 
решение(X1, X2, X3, X4, Y1, Y2, Y3, Y4) :- X1 = "ЦСКА", соответствие(X1, Y1), X2 = "Спартак", соответствие(X2, Y2),
                       X3 = "Динамо", соответствие(X3, Y3), X4 = "Ротор", соответствие(X4, Y4),
                       Y1 <> Y2, Y1 <> Y3, Y1 <> Y4, Y2 <> Y3, Y2 <> Y4, Y3 <> Y4.
 
GOAL
решение(X1, X2, X3, X4, Y1, Y2, Y3, Y4).
Ещё есть мысль использовать database, но, наверное, это можно решить и без динамической БД.

Код к задаче: «Логическая задача Prolog - Prolog (226274)»

textual
PREDICATES
nondeterm соответствие(symbol, string, string, integer, integer)
nondeterm название(string)
nondeterm место(integer)
nondeterm решение(string, string, string, string, integer, integer, integer, integer)
 
CLAUSES
название("Спартак").
название("ЦСКА").
название("Динамо").
название("Ротор").
 
место(1).
место(2).
место(3).
место(4).
 
соответствие(a, X1, X2, Y1, Y2) :- название(X1), X1 = "Спартак", название(X2), X2 = "ЦСКА", 
                   место(Y1), Y1 = 1, место(Y2), Y2 <> 4;
                   название(X1), X1 = "Спартак", название(X2), X2 = "ЦСКА", 
                   место(Y1), Y1 <> 1, место(Y2), Y2 = 4.
                   
соответствие(b, X1, X2, Y1, Y2) :- название(X1), X1 = "Спартак", название(X2), X2 = "ЦСКА", 
                   место(Y1), Y1 <> 1, Y1 <> 2, место(Y2), Y2 <> 2;
                   название(X1), X1 = "Спартак", название(X2), X2 = "ЦСКА", 
                   место(Y1), Y1 <> 3, Y1 <> 4, место(Y2), Y2 = 2.
                   
соответствие(c, X3, X2, Y3, Y2) :- название(X3), X3 = "Динамо", название(X2), X2 = "ЦСКА",
                   место(Y3), Y3 = 1, место(Y2), Y2 = 4;
                   название(X3), X3 = "Динамо", название(X2), X2 = "ЦСКА", 
                   место(Y3), Y3 <> 1, место(Y2), Y2 <> 4.
                   
соответствие(d, X3, X4, Y3, Y4) :- название(X3), X3 = "Динамо", название(X4), X4 = "Ротор",
                   место(Y3), Y3 = 2, место(Y4), Y4 <> 4;
                   название(X3), X3 = "Динамо", название(X4), X4 = "Ротор", 
                   место(Y3), Y3 <> 2, место(Y4), Y4 = 4.
 
решение(X1, X2, X3, X4, Y1, Y2, Y3, Y4) :- X2 = "ЦСКА", X1 = "Спартак", X3 = "Динамо", X4 = "Ротор", 
                       соответствие(a, X1, X2, Y1, Y2), соответствие(b, X1, X2, Y1, Y2),
                       соответствие(c, X3, X2, Y3, Y2), соответствие(d, X3, X4, Y3, Y4),
                       Y1 <> Y2, Y1 <> Y3, Y1 <> Y4, Y2 <> Y3, Y2 <> Y4, Y3 <> Y4.
GOAL
решение(X1, X2, X3, X4, Y1, Y2, Y3, Y4).

5   голосов, оценка 3.600 из 5


СОХРАНИТЬ ССЫЛКУ