比方说,我有一个规则库,它说如果我们的蛋糕不好,那么我们就不应该吃它:
do_not_eat(cake) :- is_bad(cake).
让我们进一步说我们的布朗尼蛋糕变质了:
is_bad(brownie).
我如何在Prolog中表达布朗尼应被视为蛋糕的代名词,因此不应食用蛋糕?我知道我可以用变量改写第一个规则
do_not_eat(Cake) :- is_bad(Cake)
,一切都会很好地统一。但是,我想知道是否可以说出“使brownie
与cake
同义”或“适用于cake
的任何内容都应适用于{{1 }}”?我尝试添加规则brownie
,但似乎并没有解决问题。我一直在使用GnuProlog。
答案 0 :(得分:1)
一种解决方案是将您的规则更改为:
do_not_eat(Cake) :- cake(Cake), is_bad(Cake).
并定义:
cake(brownie).
cake(cupcakes).
...
您也可以概括该解决方案。例如:
do_not_eat(Food) :- food(Food), is_bad(Food).
,然后定义:
food(Food) :- cake(Food).
一个更强大但更重的解决方案是定义代表您的概念的对象层次。然后,您可以简单地拥有从蛋糕继承的布朗尼和从食物继承的蛋糕。使用支持GNU Prolog的Logtalk:
------- cakes.lgt -------
:- object(food).
:- public(do_not_eat/0).
do_not_eat :-
% ask the receiver of the do_not_eat/0 message if it's bad
::is_bad.
:- public(is_bad/0).
:- end_object.
:- object(cake,
extends(food)).
% cakes are bad for your health
is_bad.
:- end_object.
% anything that applies to cake also applies to brownie
:- object(brownie,
extends(cake)).
:- end_object.
-------------------------
然后,您可以:
$ gplgt
...
| ?- {cakes}.
...
% (0 warnings)
(5 ms) yes
| ?- cake::do_not_eat.
yes
| ?- brownie::do_not_eat.
yes