我正在使用此代码:
item(one, 50, 40).
item(two, 80, 70).
item(three, 100, 55).
item(four, 50, 45).
maxMeanStudy:-
findall(M,item(_,M,_),L),
max_member(Max,L),
writeln(Max),!.
要访问项目的中间值,我必须使用item(_,M,_)
访问它。
如果只有几个条目,这是可以的。但如果有很多条目,则每次都很难输入item(_,_,_,_,_,M,_,_,_,_,_,_,_,_,_,_)
。
有没有办法我最初将结构声明为item(Name, Val1, Val2)
然后我可以使用item(Val1)
来访问它?
答案 0 :(得分:7)
只需定义一个辅助谓词:
md_(M) :-
item(_, M, _).
这样你只需要写一次(可能)大量的下划线一次。
使用SICStus Prolog 4.3.3的示例查询:
| ?- md_(M).
M = 50 ? ;
M = 80 ? ;
M = 100 ? ;
M = 50 ? ;
no
答案 1 :(得分:4)
可能有趣的是这段代码可以对谓词的每个arg起作用:
item(one, 50, 40).
item(two, 80, 70).
item(three, 100, 55).
item(four, 50, 45).
argStudy(Predicate, Arity, NumArg, Study_Name, V):-
compound_name_arity(L,Predicate,Arity),
findall(Args, (L, L =..[_|Args]), L_Args),
maplist(nth1(NumArg), L_Args, Lst),
call(Study_Name, Lst, V).
例如:
?- argStudy(item, 3, 2, max_list, V).
V = 100.
?- argStudy(item, 3, 2, min_list, V).
V = 50.
?- argStudy(item, 3, 2, sum_list, V).
V = 280.
?- argStudy(item, 3, 1, sort, V).
V = [four, one, three, two].
答案 2 :(得分:3)
由于arity(参数的数量)是一个独特的子句特征,你可以快速添加代码
item(Val1) :- item(_, Val1, _).
但这似乎是一个短视的选择,用于维护。
处理与许多属性(列)的关系一直是Prolog中的一个问题,因为它没有指定如何声明元数据。
使用ISO内置arg / 3构建此类图层并不困难。或者查看库(record)。 OTOH,SWI-Prolog采取了激进的离职选择,实施了非标准的延期dicts。
答案 3 :(得分:1)
易:
argValue(Index,Value,F/A) :-
functor(Pred,F,A),
Pred,
arg(Index,Pred,Value).
现在按索引选择要获取的参数:
?- argValue(3,Val,item/3).
Val = 40 ;
Val = 70 ;
Val = 55 ;
Val = 45 ;
Val = 40 ;
Val = 70 ;
Val = 55 ;
Val = 45.
?- argValue(2,Val,item/3).
Val = 50 ;
Val = 80 ;
Val = 100 ;
Val = 50 ;
Val = 50 ;
Val = 80 ;
Val = 100 ;
Val = 50.