Использование стандарта setof/3
является лучшим вариантом, поскольку позволяет легко определить более общий предикат, который может перечислять решения, когда аргумент класса не связан. Например, предположим, что следующая база данных:
has_subclass(thing,animal).
has_subclass(thing,tree).
has_subclass(thing,object).
has_subclass(animal,cat).
has_subclass(animal,dog).
has_subclass(tree,pine).
has_subclass(tree,oak).
И определение:
subclass_count(Class, Count) :-
setof(Subclass, has_subclass(Class, Subclass), Subclasses),
length(Subclasses, Count).
Пример звонка:
| ?- subclass_count(Class, Count).
Class = animal
Count = 2 ? ;
Class = thing
Count = 3 ? ;
Class = tree
Count = 2
yes
Если вы попробуете вместо одного из findall/3
решений в других ответах, вместо этого мы получим:
| ?- count_has_subclass(What, Count).
Count = 7
Но обратите внимание, что это решение также имеет разумную интерпретацию как возвращение числа всех существующих подклассов, когда класс не указан.