1

The question of the difference between a functor and a predicate in prolog is asked often.

I am trying to develop an informal definition that is suitable for new students.

A functor is the name of a predicate. The word functor is used when discussing syntax, such as arity, affix type, and relative priority over other functors. The word predicate is used when discussing logical and procedural meaning.

This looks "good enough" to me.

Question: Is it good enough, or is it fundamentally flawed?

To be clear, I am aiming to develop a useful intuition, not write legalistic text for an ISO standard!

Penelope
  • 291
  • 6
  • 1
    A functor does not need to be a clause head. I like the definitions at https://www.swi-prolog.org/pldoc/man?section=glossary#gloss:functor and https://www.swi-prolog.org/pldoc/man?section=glossary#gloss:predicate and https://www.swi-prolog.org/pldoc/man?section=glossary#gloss:clause – brebs Jan 12 '23 at 23:47
  • You are aware that the ISO definitions are the same? See: [Is this Prolog terminology correct? (fact, rule, procedure, predicate, ...)](https://stackoverflow.com/a/49931767/1243762) – Guy Coder Jan 13 '23 at 12:54
  • For me the problem is that to many people just use `predicate` when they should use a more specific term like `clause`, `predicate indicator`, `predication`, `identifier`, ... – Guy Coder Jan 13 '23 at 12:57
  • When using [predicate_property/2](https://www.swi-prolog.org/pldoc/man?predicate=predicate_property/2) came to the realization that it should be named `predication_property/2`, I know it seems a subtle change but it is a change from a one to one relationship to a one to many relationship. Learned that one the hard way when my code kept giving unexpected results. – Guy Coder Jan 13 '23 at 13:56

2 Answers2

2

The definition in https://www.swi-prolog.org/pldoc/man?section=glossary is: "functor: Combination of name and arity of a compound term. The term foo(a,b,c) is said to be a term belonging to the functor foo/3." This does not help a lot, and certainly doesn't explain the difference from a predicate, which is defined: "Collection of clauses with the same functor (name/arity). If a goal is proved, the system looks for a predicate with the same functor, then uses indexing to select candidate clauses and then tries these clauses one-by-one. See also backtracking.".

One of the things that often confuses students is that foo(a) could be a term, a goal, or a clause head, depending on the context.

One way to think about term versus predicate/goal is to treat call/1 as if it is implemented by an "infinite" number of clauses that look like this:

call(foo(X)) :- foo(X).
call(foo(X,Y)) :- foo(X,Y).
call(bar(X)) :- bar(X).

etc.

This is why you can pass around at term (which is just data) but treat it as a "goal". So, in Prolog there's no need to have a special "closure" or "thunk" or "predicate" data type - everything can be treated as just data and can be executed by use of the call/1 predicate.

(There are also variations on "call", such as call/2, which can be defined as:

call(foo, X) :- foo(X).
call(foo(X), Y) :- foo(X, Y).

etc.)

This can be used to implement "meta-predicates", such as maplist/2, which takes a list and applies a predicate to each element:

?- maplist(writeln, [one,two,three]).
one
two
three

where a naïve implementation of maplist/2 is (the actual implementation is a bit more complicated, for efficiency):

maplist(_Goal, []).
maplist(Goal, [X|Xs]) :-
    call(Goal, X),
    maplist(Goal, Xs).
Peter Ludemann
  • 985
  • 6
  • 8
  • 1
    With the exception of variables, all terms have a functor, including atoms and numbers (which have arity zero). We can characterize the set of atomic terms as all terms of arity zero. This makes SWI-Prolog glossary definition incomplete/misleading. – Paulo Moura Jan 13 '23 at 08:44
  • The full content of the glossary does say "foo/0 is used to refer to the atom `foo`" @PauloMoura. It is however incomplete since it doesn't talk about numbers. – TA_intern Jan 13 '23 at 09:03
2

The answer by Peter Ludemann is already very good. I want to address the following from your question:

To be clear, I am aiming to develop a useful intuition, not write legalistic text for an ISO standard!

If you want to develop intuition, don't bother writing definitions. Definitions end up being written in legalese or are useless as definitions. This is why we sometimes explain by describing how the machine will behave, this is supposedly well-defined, while any statement written in natural language is by definition ambiguous. It is interpreted by a human brain, and you have no idea what is in this brain when it interprets it. As a defense, you end up using legalese to write definitions in natural language.

You can give examples, which will leave some impression and probably develop intuition.

"The Prolog compound term a(b, c) can be described by the functor a/2. Here, a is the term name, and 2 is its arity".

"The functor foo/3 describes any term with a name foo and three arguments."

"Atomic terms by definition have arity 0: for example atoms or numbers. The atom a belongs to the functor a/0."

"You can define two predicates with the same name, as long as they have a different number of arguments."

There is also the possibility of confusion because some system predicates that allow introspection might take either a functor or the head of the predicate they work on. For example, abolish/1 takes a functor, while retractall/1 takes the predicate head.....

TA_intern
  • 2,222
  • 4
  • 12
  • 1
    @GuyCoder Ah don't worry about votes. Maybe I need to edit my answer to help you out with your predicament. – TA_intern Jan 13 '23 at 13:19