想象一下,我有以下知识库,为每个人提供他的名字和年龄。
person(mary, 39).
person(john, 24).
person(sandy, 17).
现在,我想找回所有超过20年的人。此外,我只想收集他们的名字,而不是他们的年龄。在这里,我想要检索mary
和john
。
如何在Prolog中更具体地在SWI-Prolog中执行此操作?
如果我们使用非匿名变量,例如:
?- person(X, Y), Y > 20.
Prolog会向我提供X
和Y
的值,我不想Y
。
我无法使用匿名变量_
,因为Prolog无法链接其两个实例。以下是错误:
?- person(X, _), _ > 20.
那么,怎么做呢?
答案 0 :(得分:7)
这个答案直接跟随@danielp的this previous answer。
使用prolog-toplevel swi-prolog,你可以拥有其中任何一个:
显示所有变量的答案替换(默认)
不显示_A
有关详细信息,请阅读您正在使用的Prolog处理器的手册!
SWI:Environment Control (Prolog flags)。
current_prolog_flag/2
。
set_prolog_flag/2
stefan@Lenovo ~ $ swipl Welcome to SWI-Prolog (Multi-threaded, 64 bits, Version 7.3.15) ... ?- current_prolog_flag(toplevel_print_anon, Flag). % get default Flag = true. ?- _A = 1. _A = 1. ?- _A = 1, X = _A. _A = X, X = 1. ?- set_prolog_flag(toplevel_print_anon, false). % toggle flag true. ?- current_prolog_flag(toplevel_print_anon, Flag). Flag = false. ?- _A = 1. % watch out! true. ?- _A = 1, X = _A. X = 1. ?- set_prolog_flag(toplevel_print_anon, true). % restore flag true. ?- current_prolog_flag(toplevel_print_anon, Flag). Flag = true. ?- _A = 1. _A = 1. ?- _A = 1, X = _A. _A = X, X = 1.
答案 1 :(得分:5)
为什么不定义谓词
ofintrest(X):- person(X,Y),Y>20.
查询
ofintrest(X).
如果您不想定义谓词,也可以使用双重否定
person(X,_) ,\+(\+ (person(X,Y), Y>20))
答案 2 :(得分:2)
您可以定义已在CAFEBABE's answer中发布的谓词。
或者,您也可以将一个以_
开头的名称赋予其值不应出现在答案中的变量(如您所知,_
的出现始终是不同的变量):
person(X,_Age), _Age > 20.
更新:这是Prolog实施所特有的。它适用于SICStus,但默认情况下不适用于SWI(请参阅repeat's answer)。