我怎么知道一个对象是否是唯一的
我只是无法理解我与prolog有关的这个问题。只是刚刚开始,但我似乎无法找到一种方法来查明对象是否是唯一的。继承人我的代码:我怎么知道一个对象是否是唯一的
/* (Student Name, Student Number)*/
Student(stuart, 11234).
Student(ross, 11235).
Student(rose, 11236).
Student(stuart, 11237).
我怎么能找出一个学生是否是独一无二的。以Stuart为例,有两个学生叫Stuart,所以Stuart并不是唯一的。我怎么能写一个程序来判断另一个学生是否叫斯图尔特。
我试过在这上面花了这么多小时,但我似乎无法控制原来的斯图尔特而不是其他斯图尔特,因为我不能排除我正在寻找的那个如果其独特的话。
感谢您的帮助。
与数据库例如,这可以做
,因为它产生
?- unique(S).
S = ross ;
S = rose ;
false.
一般来说,Prolog是朝着解决方案的存在针对性。然后关于基数的预测需要来自语言中“不纯”部分的一些支持:nb_setarg它目前是我们最好的朋友,当我们需要有效地跟踪基数。
使用这样的metapredicate:
%% count_solutions(+Goal, ?C)
%
% adapted from call_nth/2 for http://stackoverflow.com/a/14280226/874024
%
count_solutions(Goal, C) :-
State = count(0, _), % note the extra argument which remains a variable
( Goal,
arg(1, State, C1),
C2 is C1 + 1,
nb_setarg(1, State, C2),
fail
; arg(1, State, C)
).
:- meta_predicate count_solutions(0, ?).
你能解决这个问题,而不考虑第二个参数
unique(S) :-
student(S, _), count_solutions(student(S, _), 1).
相同的谓词可以使用aggregate_all(计数,学生(S,_) 1)来自库(集合),但是这个库目前在内部建立一个列表,那么你可以考虑彼得的答案更容易实现。
关于你的代码的一些评论。这不是一个事实:
Student(Ross).
这是两个不同的事实(在SWI-Prolog的,至少):
student(ross).
student('Ross').
换句话说,谓词名称必须以小写字母开始,标识出发用大写字母表示变量,而不是原子。您可以将任何字符串放在单引号中,使其成为有效的原子。
现在,这是不利的,目前还不清楚你的目标是什么。你将如何处理你的独特的学生?你怎么知道第一个是你正在寻找的那个,而不是第二个?为什么不使用学生号码(至少在你的例子中两个斯图尔特似乎有不同的数字)?
感谢您抽出一些时间来解决我的问题。是的,你说我的代码无效。这只是一个如何做独特的事情的例子。我想知道你是否可以用一种方式来表示学生是否独一无二。是的,我可以使用学生号码,但我真的很想知道一种方式,我可以告诉别人是否是独一无二的。我将要对独特的学生做什么,告诉它是否唯一 – user1816481 2013-03-09 17:56:24
可能有相当多的解决这个问题的方法,但我会做这种方式:
% a student has a name and a number
student(stuart, 11234).
student(ross, 11235).
student(rose, 11236).
student(stuart, 11237).
这段代码说“找一个列表的长度相同的学生姓名的号码”,然后“让伯爵一样的列表的长度”:
% a student name is unique (appears once and only once) is the
% number_students count is 1
unique_student(Name) :-
number_students(Name, 1).
012:
% for every student name there is an associated count of how many times
% that name appears
number_students(Name, Count) :-
findall(_, student(Name, _), Students),
length(Students, Count).
如果number_students是1此谓词只会是真实的
测试:
12 ?- unique_student(ross).
true.
13 ?- unique_student(rose).
true.
14 ?- unique_student(bob).
false.
15 ?- unique_student(stuart).
false.
这是解决问题的一种简单的方法,但因为你不能说这样的话是不是很大 Prolog的解决方案“给我一个独特的学生姓名”,并得到一个列表所有独特的名字。
+1 @CapelliC答案。这比我的好多了! – 2013-03-10 12:16:13
虽然仍然是一个很好的答案,感谢您的帮助:) – user1816481 2013-03-13 16:23:59
谢谢,我敢肯定,这是一种方法来做到这一点\ +,但我想你的解决方案处理它罚款:) – user1816481 2013-03-13 16:23:34