3 Built-in Predicates

3.1 Introduction

This section contains descriptions of the library predicates of Qu-Prolog, grouped by predicate family. The meaning of the terms used may be found in Notation.

Many of the predicates described in this section are accompanied with mode information and examples. The mode information of each argument of a predicate is represented by a pair consisting of a mode and a type.

The mode is one of

The type is one of

As an example, the mode information for =.. is
mode +nonvar =.. ?closed_list(term)
mode -nonvar =.. @closed_list(term)

The first mode deals with the case where the first argument is a nonvar at the time of call and the second argument will be a closed list of terms by the end of the call. The second mode deals with the case where the first argument is a variable at the time of call (and is instantiated to a nonvar by the end of the call) and the second argument is a closed list of terms that is unchanged by the call.

3.2 Control

This set of predicates provides control for the execution of Qu-Prolog.

Predicates:

Goal1 , Goal2

Conjunction. Goal1 and then Goal2.
mode ','(+goal, +goal)

Example:

| ?- A = 10 , B is 2 * A.

A = 10
B = 20;

no

Goal1 ; Goal2

Disjunction. Goal1 or Goal2.
mode +goal ; +goal

Example:

| ?- A = 10 ; B = 20.

A = 10
B = B;

A = A
B = 20;

no

true

Succeed.

Example:

| ?- true.

yes

\+ Goal

Negation. If Goal then fail else succeed.
mode \+ +goal

Example:

| ?- \+ (10 = 20).

yes

| ?- \+ true.

no

Goal1 -> Goal2

If Goal1 then Goal2 else fail.
mode +goal -> +goal

Example:

| ?- true -> A = 10.

A = 10;

no

| ?- \+ true -> A = 10.

no

Goal1 -> Goal2 ; Goal3

If Goal1 then Goal2 else Goal3.
mode +goal -> +goal ; +goal

Example:

| ?- true -> A = 10 ; B = 20.

A = 10
B = B;

no

| ?- \+ true -> A = 10 ; B = 20.

A = A
B = 20;

no

!

The `cut' operator removes all choices from the parent goal and any goals before the cut in the clause.

Example:

| ?- A = 10 , ! ; B = 20.

A = 10
B = B;

no

break

Start an invocation of the interpreter. The debugging state is unaffected. A control-D exits the break and returns to the previous level.

Example:

| ?- A = 10 , B = 10 , break, C = 15.

[b1] | ?- A = 15.

no

[b1] | ?- A = B.

A = 10
B = 10;

no

[b1] | ?- C = 20.

C = 20;

no

fail

Fail.

Example:

| ?- A = 10, fail ; B = 20

A = A
B = 20;

no

halt
halt(Integer)

Exit Qu-Prolog with exit code 0 or Integer.

Example:

| ?- A = 10, halt ; B = 20
Qu-Prolog exits and returns the user to the system prompt.

call(Goal)

Execute Goal. If Goal has an inline declaration then it will be expanded.
mode call(+goal)

Example:

| ?- call( (A = 10, B = 20) ).

A = 10
B = 20;

no

callable(Goal)

The same as once((atom(Goal);compound(Goal))).

initialization(Goal)

The same as call(Goal). It is included for compatibility with the ISO standard.

call_predicate(Goal)
call_predicate(Goal,Arg1)
call_predicate(Goal,Arg1,Arg2)
call_predicate(Goal,Arg1,Arg2,Arg3)
call_predicate(Goal,Arg1,Arg2,Arg3,Arg4)

Execute Goal with the required arguments. This is more direct than using call(Goal) and, from the point of view of the debugger, behaves like compiled code. Note that Goal can be higher-order, that is, Goal can include arguments.
mode call_predicate(+goal, +term, ...)

Example:

| ?- call_predicate(=, A, 10).

A = 10;

no

repeat

Succeeds repeatedly.

Example:

| ?- A = 10, repeat, B = 20.

A = 10
B = 20;

A = 10
B = 20;

A = 10
B = 20;

...

once(Goal)

Execute the Goal and discard any generated alternatives.
mode once(+goal)

Example:

| ?- once( (A = 10, repeat, B = 20) ).

A = 10
B = 20;

no

| ?- once( (A = 10 ; B = 20) ).

A = 10
B = B;

no

catch(Goal1, Template, Goal2)

Set a trap for Template during the execution of Goal1. Goal2 is executed when a term that unifies with Template is thrown.
catch/3 and throw/1 are typically used for error handling.
mode catch(+goal, +term, +goal)

throw(Template)

Throw Template to the innermost matching catch/3.
mode throw(+term)

Example:

Consider an application that carries out complex processing and may exit at various points within this processing. One way of programming this behaviour is by using catch at the top level of the application as given below.

main(Args) :-
    catch(process(Args), exit_throw(Msg), write(Msg)).

When the application is started, process(Args) is executed with a trap set that will write a message when an exit_throw(Msg) is thrown.

The application can exit at a given point within the execution of process(Args) by making a call such as

throw(exit_throw('this is my exit message'))

unwind_protect(Goal1, Goal2)

Succeed if Goal1 succeeds. Goal2 is executed after Goal1, even if Goal1 fails or exits non-locally. Goal2 is called for its side effects only, and any bindings it makes are ignored. Note that it is not currently possible to protect against halt/0 or against SIGKILL signal from the operating system.
mode unwind_protect(+goal, +goal)

Example:

Assume that a goal p is to be executed in an environment where the fact fact(a,b) is added to the dynamic database. Further assume that this fact is to be removed when the execution of p finishes with success or failure or because of a throw/1 within p, assuming that fact(a,b) is the only clause for fact/2, this can be achieved with the call
unwind_protect((assert(fact(a,b)), p), retract(fact(a,b)))

call_cleanup(Goal1, Goal2)

Calls Goal1 and whenever this call fails or succeeds deterministically, then Goal2 is called. It is similar to unwind_protect. The main difference is that unwind_protect is called on success (even if choice points remain) whereas call_cleanup is called on success only when Goal1 has no more choices.

3.3 Input / Output

3.3.1 File and Stream Handling

Streams are the basic input/output management units. They provide a uniform interface to files and strings. Each stream can be opened for reading or writing, and data is sent through the stream using term or character input/output predicates. String streams behave in the same way as file streams.

Rather than having a file attached to the stream, a string stream is connected to an atom or a list of CharCode. If the string stream is opened for writing, any further writing to the stream is not possible after the successful execution of stream_to_atom/2, stream_to_string/2 or stream_to_chars/2 as these predicates close the stream.

If the process is registered with Pedro then it is possible to open a message stream for either reading or writing.

A term representing a stream is an integer (the stream ID) generated by a call to open/[3,4] or one of the atoms stdin, user_input, stdout, user_output, stderr and user_error, or an atom declared by the user as an alias for a stream.

Predicates:

access(File, Permission, Result)

Integer contains the result of Permission check for File. Permission is an integer made up of mask bits 0,1,2,4 and is used to test if the file exists, and has execute, write and read permissions. Result is 0 if the file passes the test and -1 if it fails. The usage is identical to the Unix system call access(2).
So, for example, access(File, 3, 0) will succeed if the file is readable and writable.
mode access(@atom, @integer, ?integer)

open(File, Mode, Stream)
open(File, Mode, Stream, OptionList)

Stream is the stream resulting from opening File with the given Mode and OptionList.

Modes:

Options:


mode open(@atom, @atom, -stream)
mode open(@atom, @atom, -stream, @closed_list(gcomp))

Example:

| ?- open(filename, write, Stream),
write_term_list(Stream, [wqa('Hello World'), pc(0'.), nl]),
close(Stream).

Stream = 3

| ?- open(filename, append, Stream),
write_term_list(Stream, [wqa('Bye'), pc(0'.), nl]),
close(Stream).

Stream = 3

| ?- open(filename, read, Stream),
read(Stream, Term1),
read(Stream, Term2).

Stream = 3
Term1 = Hello World
Term2 = Bye

open_string(StringMode, Stream)
open_string(StringMode, Stream, OptionList)

Stream is the stream resulting from opening the string with the given StringMode and OptionList. Possible value for OptionList is explained in open/4. The possible values for StringMode are
mode open_string(@ground, -stream)
mode open_string(@ground, -stream, +closed_list(gcomp))

Example:

| ?- open_string(write, Stream),
write_term_list(Stream, [wqa('Hello World'), pc(0'.), nl]),
stream_to_atom(Stream, Atom).

Stream = 3
Atom = 'Hello World'.

| ?- open_string(read('p(X,Y).'), Stream),
read(Stream, Term).

Stream = 3
Term = p(B, A)

| ?- open_string(read("p(X,Y)."), Stream),
read(Stream, Term).

Stream = 3
Term = p(B, A)

open_msgstream(Handle, Mode, Stream)

This predicate opens a stream with Mode for an address given by the handle Handle. If the stream is opened for reading then messages from the sender should be of the form
p2pmsg('':myname@mymachine, Handle, msg)
where myname and mymachine are respectively the name of this process and the machine on which this process is running. Handle is the handle specified when opening the stream. The third argument, msg should be a string - it is appended to a stream buffer that can then be read from using the Qu-Prolog input predicates. Messages from this address are ignored by the predicates that look at the message buffer such as ipc_peek.

If the stream is opened for writing then when the stream is flushed, the contents of the stream buffer is wrapped into a message of the form
p2pmsg(Handle, MyHAndle, msg)

For most applications the message sends and receives are more appropriate but for interacting with GUI's it is sometimes more convenient to use streams. The xqpdebug GUI uses this mechanism.

set_std_stream(StreamNo, Stream)

This predicate resets one of the standard streams given by StreamNo to Stream. StreamNo must be 0,1 or 2 (stdin,stdout,stderr).

This is used in combination with open_msgstream in the xqpdebug GUI so that reads and writes in the debugger become reads and writes via the GUI. This allows the GUI to behave in a transparent way with respect to IO.

reset_std_stream(StreamNo)

Reset the supplied standard stream.

close(Stream)
close(Stream, OptionList)

Close the given Stream. The only possible kind of term in OptionList is
mode close(@stream)
mode close(@stream, @closed_list(gcomp))

at_end_of_stream
at_end_of_stream(Stream)

Succeed if at the end of Stream or the current input stream.
mode at_end_of_stream(@stream)

Example:

| ?- open(filename, write, Stream),
write_term_list(Stream, [wqa('Hello World'), pc(0'.), nl]),
write_term_list(Stream, [wqa('Bye'), pc(0'.), nl]),
close(Stream).

Stream = 3

| ?- open(filename, read, Stream),
at_end_of_stream(Stream),
close(ReadStream).

no

| ?- open(filename, read, Stream),
read(Stream, Term1),
read(Stream, Term2),
at_end_of_stream(Stream).

Stream = 3
Term1 = Hello World
Term2 = Bye

current_input(Stream)

The current input stream is Stream.
mode current_input(?stream)

set_input(Stream)

Change the current input stream to Stream. The initial stream is user_input.
mode set_input(@stream)

Examples (Continued from last):

| ?- open(filename, read, Stream),
set_input(Stream),
current_input(Input),
read(Term1), read(Term2),
set_input(stdin).

Stream = 3
Input = 3
Term1 = Hello World
Term2 = Bye

see(File)

Open File for reading and change the current input stream to File.
mode see(@atom)

Examples (Continued from last):

| ?- see(filename),
seeing(File),
read(Term1), read(Term2),
seen.

File = filename
Term1 = Hello World
Term2 = Bye

seeing(File)

Return the file name of the current input stream.
mode seeing(?atom)

seen

Close the current input stream. Change the stream to user_input.

current_output(Stream)

The current output stream is Stream.
mode current_output(?stream)

set_output(Stream)

Change the current output stream to Stream. The initial stream is user_output.
mode set_output(@stream)

Example:

| ?- open_string(write, Stream),
set_output(Stream),
current_output(Output),
write_term_list([wqa('Hello World'), pc(0'.), nl]),
stream_to_atom(Stream, Atom),
set_output(stdout).

Stream = 3
Output = 3
Atom = 'Hello World'.

tell(File)

Open File for writing and change the current output stream to File.
mode tell(@atom)

Example:

| ?- tell(filename),
telling(File),
write_term_list(Stream, [wqa('Hello World'), pc(0'.), nl]),
write_term_list(Stream, [wqa('Bye'), pc(0'.), nl]),
told.

File = filename

| ?- open(filename, read, Stream),
read(Stream, Term1),
read(Stream, Term2).

Stream = 3
Term1 = Hello World
Term2 = Bye

telling(File)

Return the file name of the current output stream.
mode telling(@atom)

told

Close the current output stream. Change the stream to user_output.

flush_output
flush_output(Stream)

Flush Stream or the current output stream. Forces a write on any remaining output to the stream.

set_autoflush(Stream)

Set Stream to automatically flush after each token is written. This is useful for streams that are to behave like standard error. (The default for streams is to flush only at a newline or at an explicit call to flush_output.)

set_stream_position(Stream, N)

Move Stream to the position N. The reposition flag must have been set when Stream was opened.
mode set_stream_position(@stream, @integer)

stream_property(Stream, Property)

A property of Stream is Property. The possible values for Property are given below.
mode stream_property(@stream, ?compound)

Example:

| ?- open(filename, write, Stream),
stream_property(Stream, file_name(Value)).

Stream = 3
Value = filename

stream_to_atom(Stream, Atom)

Stream specifies the output string stream where Atom can be obtained. When this predicate terminates successfully the stream is closed and any further writing to the stream is not possible.
mode stream_to_atom(@stream, -atom)

Example:

| ?- open_string(write, Stream),
write(Stream, Hello),
write(Stream, ' '),
write(Stream, World),
stream_to_atom(Stream, Atom).

Stream = 3
Hello = Hello
World = World
Atom = Hello World

stream_to_string(Stream, String)

Stream specifies the output string stream where String can be obtained. When this predicate terminates successfully the stream is closed and any further writing to the stream is not possible.
mode stream_to_string(@stream, -string)

Example:

| ?- open_string(write, Stream),
write(Stream, Hello),
write(Stream, ' '),
write(Stream, World),
stream_to_string(Stream, String).

Stream = 3
Hello = Hello
World = World
String = "Hello World"

stream_to_chars(Stream, CharCodeList)

Stream specifies the output string stream where CharCodeList can be obtained. When this predicate terminates successfully the stream is closed and any further writing to the stream is not possible.
mode stream_to_chars(@stream, -closed_list(integer))

Example:

| ?- open_string(write, Stream),
write(Stream, Hello),
write(Stream, ' '),
write(Stream, World),
stream_to_chars(Stream, Chars).

Stream = 3
Hello = Hello
World = World
Chars = [72, 101, 108, 108, 111, 32, 87, 111, 114, 108, 100]

An example of the use of string streams is for determining where information will appear in output to a user interface. The following definitions may be used to retrieve the character positions of matching bracket pairs of a supplied term (assuming the character position of the first character of the term is in position one).

brackets(Term, Brackets) :-
open_string(write, Stream),
write(Stream, Term),
stream_to_chars(Stream, CharList),
match_brackets(CharList, 1, [], Brackets).
match_brackets([], _, _, []).
match_brackets([C|Rest], CurrPos, LeftBr, Brackets) :-
NewCurrPos is CurrPos + 1,
( C = 0'( % open bracket
  ->
    match_brackets(Rest, NewCurrPos, [CurrPos|LeftBr], Brackets)
  ;
  C = 0') % close bracket
  ->
    LeftBr = [LBPos|LBRest],
    Brackets = [(LBPos - CurrPos)|Brackets1],
    match_brackets(Rest, NewCurrPos, LBRest, Brackets1)
  ;
    match_brackets(Rest, NewCurrPos, LeftBr, Brackets)
).

Given the above definitions, the system will behave as follows.

| ?- brackets(f(XYZ, g(a, XYZ), h(b)),B).

XYZ
B = [9 - 16, 20 - 22, 2 - 23];

no

| ?- write(f(XYZ, g(a, XYZ), h(b))).

f(XYZ, g(a, XYZ), h(b))
XYZ = XYZ;

no

get_open_streams(Streams)

Retrieve a list of all the current open streams.

3.3.2 Term Input/Output

For input/output predicates, if the stream is specified explicitly, the stream appears as the first argument. Otherwise, the current input/output stream is assumed.

Qu-Prolog supports multiple operator tables and object variable prefix tables. At any time, there is one active operator table and one active object variable prefix table. Active tables can be changed and new tables can be created by op_table/1 and obvar_prefix_table/1. When a new operator table is created, the comma `,' operator is automatically declared. An inheritance mechanism is also available for operator tables. The input/output predicates can use a table other than the current active table by specifying the name of the table in the OptionList.

The input/output predicates are enhanced with the ability to remember the association between the ASCII representation and the internal representation for both meta and object variables over multiple input/output operations. This enables the user to refer to the same variable over a number of input/output operations, and is useful in applications with interactive environments, such as interactive theorem provers. The association is not remembered for any variable that begins with an underscore (`_').

Qu-Prolog supports high-speed input/output using byte-encoded Qu-Prolog terms. Byte-encoded terms are written with encoded_write_term/3 and read with encoded_read_term/3. The compiler can accept byte-encoded files as input and generates some intermediate files in this form (see the online manual qc(1) for further details). consult/1 also accepts such files as input. The system is supplied with a decoder for byte-encoded terms (see the online manual qecat(1) for further details).

Predicates:

op_table(Table)

Retrieve or change the current operator table. The initial table is user. Each new table is initialised with a comma `,' when it is first created.
mode op_table(?atom)

Example:

| ?- op_table(Table).

Table = user;

no

| ?- op_table(mine).

yes

| ?- op_table(Table).

Table = mine;

no

op_table_inherit(Table1, Table2)

Table1 inherits all the operators declared in Table2. These operators do not include the ones which are inherited by Table2 from a third table. That is, inheritance is non-transitive.
mode op_table_inherit(@atom, @atom)

Examples (Continued from last):

| ?- op_table_inherit(mine, user).

yes

current_op(Precedence, Associativity, Operator)
current_op(Table, Precedence, Associativity, Operator)

Operator is an operator in Table
(default: the current operator table) with Precedence and Associativity.
mode current_op(?integer, ?atom, ?atom)
mode current_op(@atom, ?integer, ?atom, ?atom)

Examples (Continued from last):

| ?- current_op(700, Assoc, Op).

Assoc = xfx
Op = =;

Assoc = xfx
Op = \=;

Assoc = xfx
Op = ?=;

Assoc = xfx
Op = ==

op(Precedence, Associativity, Operator)
op(Table, Precedence, Associativity, Operator)

Declare Operator with Precedence and Associativity as an operator in Table or in the current operator table. Precedence is any number between 0 and 1200, where higher numbers given lower precedence (loose binding).
fx Prefix. Argument has lower precedence than operator.
fy Prefix. Argument has the same precedence as operator.
quant Quantifier. Argument has the same precedence as operator.
xfx Infix. Not associative.
xfy Infix. Right associative.
yfx Infix. Left associative.
xf Postfix. Argument has lower precedence than operator.
yf Postfix. Argument has the same precedence as operator.

If Precedence is 0, any previous declaration is removed.
mode op(@integer, @atom, @atom)
mode op(@atom, @integer, @atom, @atom)

Example: (Continued from last):

| ?- op(0, yfx, '+').

yes

| ?- current_op(Prec, Assoc, '+').

Prec = 200
Assoc = fy;

no

| ?- op(500, yfx, '+').

yes

obvar_prefix_table(Table)

Retrieve or change the current object variable prefix table. The initial table is user.
mode obvar_prefix_table(?atom)

Example:

| ?- obvar_prefix_table(Table).

Table = user;

no

| ?- obvar_prefix_table(mine).

yes

| ?- obvar_prefix_table(Table).

Table = mine;

no

current_obvar_prefix(Atom)
current_obvar_prefix(Table, Atom)

Atom is an object variable prefix in Table
(default: the current object variable prefix table).
mode current_obvar_prefix(?atom)
mode current_obvar_prefix(@atom, ?atom)

Examples (Continued from last):

| ?- current_obvar_prefix(Atom).

no

obvar_prefix(AtomList)
obvar_prefix(Table, AtomList)

Declares all the atoms in AtomList as object variable prefixes in Table or the current object variable prefix table. This also implicitly declares all variant names produced by extending the variable name with a combination of underscores and sequences of digits and letters. The name of the constant being declared as an object variable prefix must be made up of lower case letters.
mode obvar_prefix(@closed_list(atom))
mode obvar_prefix(@atom)
mode obvar_prefix(@atom, @closed_list(atom))
mode obvar_prefix(@atom, @atom)

Examples (Continued from last):

| ?- obvar_prefix(a).

yes

| ?- obvar_prefix(user, [x , y , z]).

yes

| ?- current_obvar_prefix(Atom).

A = a;

no

| ?- current_obvar_prefix(user, Atom).

A = x;

A = y;

A = z;

no

remove_obvar_prefix(Atom)
remove_obvar_prefix(Table, Atom)

Remove the object variable prefix specified by Atom from Table or the current object variable prefix table.
mode remove_obvar_prefix(@atom)
mode remove_obvar_prefix(@atom, @atom)

Examples (Continued from last):

| ?- remove_obvar_prefix('a').

yes

| ?- remove_obvar_prefix(user, 'z').

yes

| ?- current_obvar_prefix(Atom).

no

| ?- current_obvar_prefix(user, Atom).

A = x;

A = y;

no

obvar_name_to_prefix(Atom, Atom)

Strips any trailing numbers or underscores from the first Atom and unifies the result with the second Atom. This predicate does not actually check whether the computed prefix is, in fact, a current object variable prefix. It is merely provided for convenience.
mode obvar_name_to_prefix(@atom, ?atom)

Examples (Continued from last):

| ?- obvar_name_to_prefix('!_a_1', A).

A = !_a;

no

| ?- obvar_name_to_prefix('y_28_1_3', A).

A = y;

no

set_obvar_name(ObVar, Name)

Set ObVar to have the base name Name. A suffix will be added to Name to complete the final name for ObVar. If ObVar has a name already, the predicate fails. See obvar_prefix/[1,2].
mode set_obvar_name(+obvar, @atom)

Example:

| ?- set_obvar_name(!_y_3, x).

_y_3 = !x_0;

no

set_var_name(Var, Name)

Set Var to have the base name Name. A suffix will be added to Name to complete the final name for Var. If Var has a name already, the predicate fails.
mode set_var_name(+obvar, @atom)

Example:

| ?- set_var_name(_32, 'X').

_32 = X_0;

no

get_var_name(Variable, Name)

Variable has Name. Fails if Variable has no name.
mode get_var_name(@anyvar, ?atom)

Examples (Assuming x is still a current object variable prefix):

| ?- get_var_name(Max, Name), write(Name), nl, fail.
Max

no

| ?- get_var_name(_32, Name), write(Name), nl, fail.

no

| ?- get_var_name(!x_3, Name), write(Name), nl, fail.
x_3

no

get_unnamed_vars(Term, VarList)

VarList is the list of unnamed (object) variables in Term.
mode get_unnamed_vars(@term, -closed_list(anyvar))

Examples (Assuming x is still a current object variable prefix):

| ?- get_unnamed_vars((A, _Y, !x, !_y), Vars),
write(Vars), fail.
[_117, !_x0]

no

name_vars(Term)
name_vars(Term, VarList)

Name all unnamed (object) variables in Term returning them in VarList.
mode name_vars(+term)
mode name_vars(+term, -closed_list(anyvar))

Example:

| ?- Term = f(X, _Y, !x, !_x), write(Term) , nl, fail.
f(X, _F5, !x, !_x0)

no

| ?- Term = f(X, _Y, !x, !_x), name_vars(Term),
write(Term), nl, fail.
f(X, A, !x, !x0)

no

error(Term)

Write Term to user_error.
mode error(@term)

Example:

| ?- error('Hello'), error(' '), error('World').
Hello World
yes

errornl(Term)
errornl

Write Term and a newline to user_error, or write a newline to user_error.
mode errornl(@term)

Example:

| ?- errornl('Hello'), errornl('World').
Hello
World

yes

read(Term)
read(Stream, Term)

Read Term from Stream or the current input stream.
mode read(?term)
mode read(@stream, ?term)

Example:

| ?- read(Term), write(Term), nl, fail.
f(X, _Y, !x, !_x)
f(_1A2, _19D, !_x0, !_x1)

no

read_term(Term, OptionList)
read_term(Stream, Term, OptionList)

Read Term from Stream or the current input stream. OptionList is a list whose entries are chosen from the items given below.
  1. Input Options
    Input options not mentioned in OptionList take on their default values.
    • remember_name(Value)
      Remember the names for all the variables other than those beginning with an underscore in Term.
      (Default: false.)
    • op_table(Value)
      Use the operator table given in Value.
      (Default: Current table.)
    • obvar_prefix_table(Value)
      Use the object variable prefix table given in Value.
      (Default: Current table.)
  2. Output Options.
    The Value for each output option is instantiated during the reading of Term.
    • variables(Value)
      All variables, including anonymous variables, from left to right.
      (Default: [].) Typically Value is a variable that is bound to the list of variables appearing in the term.
    • variable_names(Value)
      Variable=Name pairs, excluding anonymous variables.
      (Default: [].)
    • singletons(Value)
      Variable=Name pair for all singleton variables, excluding anonymous variables.
      (Default: [].)

mode read_term(?term, +closed_list(compound))
mode read_term(@stream, ?term, +closed_list(compound))

Example:

| ?- read_term(Term, []), write(Term), nl.
f(X, _Y, !x, !_x)
f(_3BE, _3B4, !_x0, !_x1)

Term = f(A, B, !x0, !x1)
| ?- read_term(Term, [variables(Var)]),
write(Var), nl, fail.

f(X, _Y, !x, !_x)
[_1F1, _1EC, !_x0, !_x1]

no

| ?- read_term(Term, [variable_names(Var)]),
write(Var), nl, fail.
f(X, _Y, !x, !_x)
[_1F1 = X, _1EC = _Y, !_x0 = x, !_x1 = _x]

no

| ?- read_term(Term, [remember_name(true)]),
write(Term), nl, fail.
f(X, _Y, !x, !_x)
f(X, _1DC, !x, !_x0)

no

read_1_term(Term, VariableNames)
read_1_term(Stream, Term, VariableNames)

Read Term from Stream or the current input stream. Return the list of variables and their names in VariableNames.
It is the same as read_term(Term, [variable_names(VariableNames)]).
mode read_1_term(?term, -closed_list(compound))
mode read_1_term(@stream, ?term, -closed_list(compound))

Example:

| ?- read_1_term(Term, Var), write(Var), nl, fail.
f(X, _Y, !x, !_x)
[_1F1 = X, _1EC = _Y, !_x0 = x, !_x1 = _x]

no

readR(Term)
readR(Stream, Term)

Read Term from Stream or the current input stream. Remember the names for all the variables other than those beginning with an underscore in Term.
It is the same as
read_term(Term, [remember_name(true)])

mode readR(?term)
mode readR(@stream, ?term)

Example:

| ?- readR(Term), write(Term), nl, fail.
f(X, _Y, !x, !_x)
f(X, _1DC, !x, !_x0)

no

readR_1_term(Term, VariableNames)
readR_1_term(Stream, Term, VariableNames)

Read Term from Stream or the current input stream. Remember the names for all the variables in Term, and return the list of variables and their names in VariableNames.
It is the same as
read_term(Term, [variable_names(VariableNames),
                 remember_name(true)])

mode readR_1_term(?term, -closed_list(compound))
mode readR_1_term(@stream, ?term, -closed_list(compound))

Example:

| ?- readR_1_term(Term, Var), write(Term), nl,
write(Var), nl, fail.
f(X, _Y, !x, !_x)
f(X, _217, !x, !_x0)
[X = X, _217 = _Y, !x = x, !_x0 = _x]

no

encoded_read_term(Term, OptionList)
encoded_read_term(Stream, Term, OptionList)

Read Term from the encoded stream Stream or the current input stream. The OptionList is the same as for read_term/[2,3].
mode encoded_read_term(@term, +closed_list(compound))
mode encoded_read_term(@stream, @term, +closed_list(compound))

write(Term)
write(Stream, Term)

Write Term to Stream or the current output stream.
mode write(?term)
mode write(@stream, ?term)

Example:

| ?- write(f(X, _Y, !x, !_x)), nl, fail.
f(X, _D0, !x, !_x0)

no

write_term(Term, OptionList)
write_term(Stream, Term, OptionList)

Write Term to Stream or the current output stream. OptionList is a list whose entries are chosen from the items given below. Items not mentioned in OptionList take on their default values.
mode write_term(@term, @closed_list(compound))
mode write_term(@stream, @term, @closed_list(compound))

Example:

| ?- write_term(f(X, _Y, !x, !_y), [remember_name(true)]),
nl, fail.
f(X, A, !x, !x0)

no


writeR(Term)
writeR(Stream, Term)
writeq(Term)
writeq(Stream, Term)
writeRq(Term)
writeRq(Stream, Term)
writeT(Term, Table)
writeT(Stream, Term, Table)
writeRT(Term, Table)
writeRT(Stream, Term, Table)
writeTq(Term, Table)
writeTq(Stream, Term, Table)
writeRTq(Term, Table)
writeRTq(Stream, Term, Table)
Write Term to Stream or the current output stream. The trailing R, T, q determine if variable names are to be created and remembered, if an operator table is to be used, and if unsafe atoms are to be quoted. These variants are faster than using the option list method above.
mode write{R,q}(@term)
mode write{R,q}(@stream, @term)
mode write{R,T,q}(@term, @atom)
mode write{R,T,q}(@stream, @term, @atom)

Example:

| ?- writeR(f(X, _Y, !x, !_y)), nl, fail.
f(X, A, !x, !x0)

no

write_atom(Atom)
write_atom(Stream, Atom)
writeq_atom(Atom)
writeq_atom(Stream, Atom)

Write Atom to Stream or the current output stream. write_atom is faster than write as it avoids many of the tests in write. Unsafe atoms are quoted if writeq_atom is used.
mode write_atom(@atom)
mode write_atom(@stream, @atom)

Example:

| ?- write_atom('Hello'), nl, fail.
Hello

no

| ?- writeq_atom('Hello'), nl, fail.
'Hello'

no

write_canonical(Term)
write_canonical(Stream, Term)

Write Term to Stream or the current output stream. All the operators are written in structural format.

It is the same as write_term(Term, [ignore_ops(True)]).
mode write_canonical(@term)
mode write_canonical(@stream, @term)

Example:

| ?- write_canonical((A = B + C * D)), nl, fail.
(=)(A, (+)(B, (*)(C, D)))

no

write_integer(Stream, Integer)

Write Integer to Stream. write_integer is faster than write as it avoids many of the tests in write.
mode write_integer(@integer)
mode write_integer(@stream, @integer)

Example:

| ?- write_integer(stdout, 42), nl, fail.
42

no

write_term_list(Message)
write_term_list(Stream, Message)

Write terms to Stream or the current output stream according to the formatting information in the list Message described below. The Qu-Prolog compiler unfolds this predicate to low-level calls to carry out the writing and is therefore the most efficient way to output a sequence of terms. The call write_term_list(stdout, Message) is faster than write_term_list(Message) because the current output stream does not need to be looked up.
mode write_term_list(@closed_list(term))
mode write_term_list(@stream, @closed_list(term))

Example:

| ?- write_term_list([wa('Hello'), sp, wa('World'), nl,
wqa('Hello World'), pc(0'!)]), nl, fail.
Hello World
'Hello World'!

no

| ?- write_term_list([wi(42), tab(5), w(f(X, _Y, !x, !_x)), sp,
pc(0'-), sp, wRq(f(X, _Y, !x, !_x)), nl,
wl([31, 12, 1999], '/')]), nl, fail.
42     f(X, _197, !x, !_x0) - f(X, A, !x, !x0)
31/12/1999

no

encoded_write_term(Term, OptionList)
encoded_write_term(Stream, Term, OptionList)

Write Term to the encoded stream Stream or the current output stream. The OptionList is the same as for write_term/[2,3].
mode encoded_write_term(+term, +closed_list(compound))
mode encoded_write_term(@stream, +term, +closed_list(compound))

portray_clause(Clause)
portray_clause(Stream, Clause)

Pretty print Clause in Stream or the current output stream.
mode portray_clause(@compound)
mode portray_clause(@stream, @compound)

Example:

| ?- portray_clause((p(X,Y) :- q(X,Z), r(Z,Y), s(Y))), fail.
p(X, Y) :-
    q(X, Z),
    r(Z, Y),
    s(Y).
no

3.3.3 Character Input/Output

These predicates can be divided into two categories according to the representation of the character used. The _char predicates deal with the character as a single letter atom. The _code predicates handle the character in its character code representation, which is an integer. Any predicate without these suffixes are intended to be compatible with existing Prologs, which use character codes. Predicates without a stream argument use the current input/output stream.

Predicates:

get(CharCode)
get(Stream,CharCode)

Get the next visible character from the current input stream, and unify it with CharCode.
mode get(?integer)
mode get(@stream, ?integer)

Note: non-visible characters are character codes less than 33. This includes:
Tab Character code: 9
New line Character code: 10
Space Character code: 32

Examples (In the second example, a 'tab' precedes the 'A'):

| ?- get(CharCode).
A

CharCode = 65

| ?- get(CharCode).
     A

CharCode = 65

get0(CharCode)
get0(Stream,CharCode)

Get the next character from the current input stream, and unify it with CharCode. The same as get_code/[1,2].
mode get0(?integer)
mode get0(@stream, ?integer)

Examples (In the second example, a 'tab' precedes the 'A'):

| ?- get0(CharCode).
A

CharCode = 65

| ?- get0(CharCode).
     A

CharCode = 9

get_char(Character)
get_char(Stream, Character)

Character is the next character from Stream or the current input stream.
mode get_char(?atom)
mode get_char(@stream, ?atom)

Example:

| ?- get_char(Char).
A

Char = A

no

get_code(CharCode)
get_code(Stream, CharCode)

CharCode is the next character code from Stream or the current input stream.
mode get_code(?integer)
mode get_code(@stream, ?integer)

Examples (In the second example, a 'tab' precedes the 'A'):

| ?- get_code(CharCode).
A

CharCode = 65

| ?- get_code(CharCode).
     A

CharCode = 9

get_line(String)
get_line(Stream, String)

String is the next line from Stream or the current input stream. The newline is consumed but is not part of the returned list. String is instantiated to -1 at EOF.
mode get_line(?string)
mode get_line(@stream, ?string)

put_line(CodeList)
put_line(Stream, CodeList)

CodeList is written to Stream or the current output stream. A newline is added.
mode put_line(@list(integer))
mode put_line(@string)
mode put_line(@stream, @list(integer))
mode put_line(@stream, @string)

Example:

| ?- get_line(L),put_line(L).
abc

abc

L = "abc"

skip(CharCode)
skip(Stream, CharCode)

Skip the input from Stream or the current input stream until after the first occurrence of CharCode. It is assumed that CharCode occurs in Stream.
mode skip(@integer)
mode skip(@stream, @integer)

Example:

| ?- skip(0'*), get_char(Char).
ABC*DEF*GHI

Char = D;

no

nl
nl(Stream)

Write a new line on Stream or the current output stream.
mode nl(@stream)

Example:

| ?- write('Hello'), nl, write('World'), nl.
Hello
World

yes

tab(N)
tab(Stream, N)

Output N spaces to Stream or the current output stream.
mode tab(@integer)
mode tab(@stream, @integer)

Example:

| ?- write('Hello'), tab(5), write('World'), nl.
Hello     World

yes

put(CharCode)

Send CharCode to the current output stream.
mode put(@integer)

Example:

| ?- put(0'H), put(0'e), put(0'l), put(0'l), put(0'o), nl.

Hello

yes

put_code(CharCode)
put_code(Stream, CharCode)

Send the character code, CharCode, to Stream or the current output stream.
mode put_code(@integer)
mode put_code(@stream, @integer)

Example:

| ?- put_code(0'H), put_code(0'e), put_code(0'l),
put_code(0'l), put_code(0'o), nl.

Hello

yes

put_char(Character)
put_char(Stream, Character)

Send Character to Stream or the current output stream.
mode put_char(@atom)
mode put_char(@stream, @atom)

Example:

| ?- put_char('H'), put_char(e), put_char(l),
put_char(l), put_char(o), nl.
Hello

yes

3.4 Terms

3.4.1 Comparison of Terms

Two terms are compared according to the standard ordering, which is defined below. Items listed at the beginning come before the items listed at the end. For example, meta variables are less than object variables in the standard ordering.

  1. Meta variables, in age ordering (older variables come before younger variables). If the variables are the same and there are substitutions, then the substitutions are compared as lists using the standard ordering.
  2. Object variables, in age ordering (older variables come before younger variables). If the variables are the same and there are substitutions, then the substitutions are compared as lists using the standard ordering.
  3. Integers, in numerical ordering.
  4. Atoms, in character code (ASCII) ordering.
  5. Compound terms (including lists) are compared in the following order:
    1. Arity, in numerical ordering.
    2. Functor, in standard ordering.
    3. Arguments, in standard ordering, from left to right.
    If the terms are the same and there are substitutions, then the substitutions are compared as lists using the standard ordering.
  6. Quantified terms are compared in the following order:
    1. Quantifier, in standard ordering.
    2. Bound variables list, in standard ordering.
    3. Body, in standard ordering.
    If the terms are the same and there are substitutions, then the substitutions are compared as lists using the standard ordering.

Predicates:

Term1 == Term2

Term1 and Term2 are alpha-equivalent without instantiation.
mode @term == @term

Example:

| ?- 10 * 2 == 10 + 10.

no

| ?- A == 10 * 2.

no

| ?- A = 10 * 2, A == 10 * 2.

A = 10 * 2;

no

Term1 \== Term2

Term1 and Term2 are not alpha-equivalent without instantiation.
mode @term \== @term

Example:

| ?- 10 * 2 \== 10 + 10.

yes

| ?- A = 10 * 2, A \== 10 * 2.

no

Term1 @= Term2

Term1 equals to Term2 in the standard order.
mode @term @= @term

Term1 @< Term2

Term1 precedes Term2 in the standard order.
mode @term @< @term

Term1 @=< Term2

Term1 precedes or equals to Term2 in the standard order.
mode @term @=< @term

Term1 @> Term2

Term1 follows Term2 in the standard order.
mode @term @> @term

Term1 @>= Term2

Term1 follows or equals to Term2 in the standard order.
mode @term @>= @term

compare(Operator, Term1, Term2)

The relation Operator holds between Term1 and Term2.
The possible choices of Operator are given below.
= If @=/2 holds.
< If @</2 holds.
> If @>/2 holds.

mode compare(?atom, @term, @term)

3.4.2 Testing of Terms

These testing predicates are used to determine various properties of the data objects, or apply constraints to the data objects.

Predicates:

simple(Term)

Succeed if Term is atomic or any variable.
mode simple(@term)

Example:

| ?- simple(atom).

yes

| ?- simple(10).

yes

| ?- simple(Var).

Var = Var

| ?- simple(!obvar).

obvar = !obvar

| ?- simple([a/!x]Var).

x = !x
Var = Var
| ?- simple(functor(arg1, arg2)).

no

| ?- simple([list1, list2]).

no

| ?- simple(!!quant !x Var).

no

atomic(Term)

Succeed if Term is an atom or a number.
mode atomic(@term)

Example:

| ?- atomic(atom).

yes

| ?- atomic(10).

yes

| ?- atomic(Var).

no

atom(Term)

Succeed if Term is an atom.
mode atom(@term)

Example:

| ?- atom(atom).

yes

| ?- atom(10).

no

number(Term)

Succeed if Term is a number.
mode number(@term)

Example:

| ?- number(10).

yes

| ?- number(3.4).

yes

| ?- number(atom).

no

integer(Term)

Succeed if Term is an integer.
mode integer(@term)

Example:

| ?- integer(10).

yes

| ?- integer(3.4).

no

| ?- integer(atom).

no

float(Term)

Succeed if Term is a double.
mode float(@term)

Example:

| ?- float(10).

no

| ?- float(3.4).

yes

| ?- float(atom).

no

any_variable(Term)

Term is a meta or an object variable.
mode any_variable(@term)

Example:

| ?- any_variable(Var).

Var = Var

| ?- any_variable(!obvar).

obvar = !obvar

| ?- any_variable([a/!x]Var).

x = !x
Var = Var

| ?- any_variable(atom).

no

| ?- any_variable(f(G)).

no

var(Term)

Succeed if Term is a meta variable.
mode var(@term)

Example:

| ?- var(Var).

Var = Var

| ?- var(!obvar).

no

| ?- var([a/!x]Var).

x = !x
Var = Var

nonvar(Term)

Succeed if Term is not a meta variable.
mode nonvar(@term)

Example:

| ?- nonvar(Var).

no

| ?- nonvar(!obvar).

obvar = !obvar

| ?- nonvar([a/!x]Var).

no

| ?- nonvar(f(G)).

G = G

ground(Term)

Succeed if Term does not contain any meta variables (after simplifying substitutions).
mode ground(@term)

Example:

| ?- ground(Var).

no

| ?- ground(!obvar).

obvar = !obvar

| ?- ground([a/!x]Var).

no

| ?- ground(f(G)).

no

obvar(Term)

Succeed if Term is an object variable.
mode obvar(@term)

Example:

| ?- obvar(Var).

no

| ?- obvar(!obvar).

obvar = !obvar

| ?- obvar([a/!x]!y).

x = !x
y = !y
no

compound(Term)

Succeed if Term is a structure or a list.
mode compound(@term)

Example:

| ?- compound(f(arg1, g(arg2))).

yes

| ?- compound([list1, list2]).

yes

| ?- compound(!!qant !x Var).

no

| ?- compound(atom).

no

| ?- compound(Var).

no

| ?- compound([a/!x]Var).

no

list(Term)

Term is a (possibly empty) list.
mode list(@term)

Example:

| ?- list(f(arg1, arg2)).

no

| ?- list([list1, list2]).

yes

| ?- list([a/!x]Var).

no

string(Term)

Term is a string.
mode string(@term)

Example:

| ?- string([40,41]).

no

| ?- string("ab").

yes

quant(Term)

Succeed if Term is a quantified term.
mode quant(@term)

Example:

| ?- quant(!!quant !x Var).

x = !x
Var = Var

| ?- quant(f(!!quant !x Var)).

no

| ?- quant([a/!x]Var).

no

sub(Term)

Succeed if Term has a substitution at the outermost level.
mode sub(@term)

Example:
| ?- sub([a/!x]Var).

x = !x
Var = Var

| ?- sub(f([a/!x]Var)).

no

std_var(Term)

Equivalent to var(Term), \+ sub(Term) but faster.
mode std_var(@term)

Example:

| ?- std_var(Var).

Var = Var

| ?- std_var([A/!a]Var).

no

std_nonvar(Term)

Equivalent to nonvar(Term), \+ sub(Term) but faster.
mode std_nonvar(@term)

std_compound(Term)

Term is compound with an atom as the functor.
mode std_compound(@term)

identical_or_apart(Term1, Term2)

True when the terms Term1 and Term2 are either identical or non-unifiable.
mode identical_or_apart(@term, @term)

Example:

| ?- identical_or_apart(A, B).

no

| ?- A is 10, identical_or_apart(A,B).

no

| ?- A is 10, B is 10, identical_or_apart(A,B).

A = 10
B = 10

| ?- A is 10, B is 20, identical_or_apart(A,B).

A = 10
B = 20

is_free_in(ObVar, Term)
is_not_free_in(ObVar, Term)

Succeed if ObVar is known to be (not) free in Term.

Both is_free_in and is_not_free_in are infix operators.
mode is_free_in(@obvar, @term)
mode is_not_free_in(@obvar, @term)

Example:

| ?- !x is_free_in f(!y, !x, !z).

x = !x
y = !y
z = !z

| ?- !x is_free_in f(!y, g(!x), !z).

x = !x
y = !y
z = !z

| ?- !x is_free_in f(X).

no

| ?- !x is_free_in atom.

no

| ?- !x is_free_in !!q !x B.

no

| ?- !x is_free_in [a/!x]B.

no

| ?- !x is_not_free_in f(!y, !x, !z).

no

| ?- !x is_not_free_in f(!y, g(!x), !z).

no

| ?- !x is_not_free_in f(X).

no

| ?- !x is_not_free_in atom.

x = !x

| ?- !x is_not_free_in !!q !x B.

x = !x
B = B

| ?- !x is_not_free_in [a/!x]B.

x = !x
B = B

not_free_in(ObVar, Term)

Apply the not free in constraint. not_free_in is an infix operator.
mode not_free_in(+obvar, +term)

Example:

| ?- !x not_free_in f(!y, !x, !z).

no

| ?- !x not_free_in f(!y, !z).

x = !x
y = !y
z = !z
provided:

!z not_free_in [!x]
!y not_free_in [!x]
!x not_free_in [!z, !y]

| ?- !x is_not_free_in f(!y, !z).

no

| ?- !x not_free_in !y, !x not_free_in !z, !x is_not_free_in f(!y, !z).

x = !x
y = !y
z = !z
provided:

!z not_free_in [!x]
!y not_free_in [!x]
!x not_free_in [!z, !y]

is_distinct(ObVar1, ObVar2)

Succeed if ObVar1 and ObVar2 are known to represent different object-level variables.
mode is_distinct(@term, @term)

Example:

| ?- is_distinct(!x, !y).

no

| ?- !x not_free_in !y, is_distinct(!x, !y).

x = !x
y = !y
provided:

!y not_free_in [!x]
!x not_free_in [!y]

check_binder(VarList, DistinctList)

Check VarList is a valid bound variable list for a quantified term. The check also ensures every object variable in the list is different from every other. The variables in VarList are made distinct from the object variables in DistinctList, which is a closed list. If VarList is an open list, the call will be delayed when the variable representing the open end of the list is reached. This is not expected to be used directly. It is called automatically by the system when quantified terms are constructed.

3.4.3 Term Manipulation

This set of meta-logical predicates perform various operations over the data objects. These operations include composition/decomposition of terms, conversion of a data object from one form to another, and simplification.

Predicates:

Term =..[Functor|Arguments]

Term is a compound composed of Functor and Arguments.
mode +nonvar =.. ?cloded_list(term)
mode -nonvar =.. @cloded_list(term)

Example:

| ?- f(a, B, _C, !d, !_e) =.. List, write(List), nl, fail.
[f, a, B, _119, !d, !_x0]

no

| ?- Funct =.. [f, a, B, _C, !d, !_e], write(Funct), nl, fail.
f(a, B, _114, !d, !_x0)


no

| ?- f(g(a), h(b)) =.. List, write(List), nl, fail.
[f, g(a), h(b)]

no

functor(Term, Functor, Arity)

Term is compound with Functor and Arity.
mode functor(-compound, +term, +integer)
mode functor(-atomic, +term, +integer)
mode functor(+compound, ?term, ?integer)
mode functor(@atomic, ?term, ?integer)

Example:

| ?- functor(f(X), Funct, Arg).

X = X
Funct = f
Arg = 1

| ?- functor(Term, f(X), 1).

Term = f(X)(A)
X = X

arg(N, Term, Argument)

The N-th argument of Term is Argument.
mode arg(@integer, +compound, +term)

If Term has no N-th argument then an out-of-range exception will occur.

Example:

| ?- arg(2, f(a, B, c), b).

B = b

| ?- arg(3, f(a, B, c), C).

B = B
C = c

| ?- arg(4, f(a, b, c), Arg).
Unrecoverable error: argument 1 of arg(4, f(a, b, c), _128)
must be in range (see manual)

no

same_args(Term1, Term2, N1, N2)

Succeed when Term1 and Term2 are both atomic or compound and the arguments from position N1 to N2 in Term1 and Term2 are the same.
mode same_args(+compound, +compound, @integer, @integer)
mode same_args(@atomic, @atomic, @integer, @integer)
mode same_args(+compound, @atomic, @integer, @integer)
mode same_args(@atomic, +compound, @integer, @integer)

Example:

| ?- same_args(f(a,b,c,d), g(A,B,C), 1, 2).

A = a
B = b
C = C

same_args(Term1, Term2, N1, N2, N3)

Succeed when Term1 and Term2 are both atomic or compound and the arguments from position N1 to N2 of Term1 are the same as the arguments from position N3 to N3-N1+N2 of Term2.
mode same_args(+compound, +compound, @integer, @integer, @integer)
mode same_args(@atomic, @atomic, @integer, @integer, @integer)
mode same_args(+compound, @atomic, @integer, @integer, @integer)
mode same_args(@atomic, +compound, @integer, @integer, @integer)

atom_chars(Atom, AtomList)

AtomList is the list of single character atoms corresponding to the successive characters of Atom.
mode atom_chars(@atom, ?closed_list(atom))
mode atom_chars(-atom, @closed_list(atom))

Example:

| ?- atom_chars(abc, Chars).

Chars = [a, b, c]

| ?- atom_chars(Atom,[a,b,c]).

Atom = abc

atom_codes(Atom, CharCodeList)

CharCodeList is the list of character codes corresponding to the successive characters of Atom.
mode atom_codes(@atom, ?closed_list(integer))
mode atom_codes(-atom, @closed_list(integer))

Example:

| ?- atom_codes(atom, Chars).

Chars = [97, 116, 111, 109]

| ?- atom_codes(Atom, [97, 116, 111, 109]).

Atom = atom

| ?- atom_codes(Atom,"atom").

Atom = atom

name(Atom, CharCodeList)

Atom is made of the character codes in CharCodeList.
mode name(@atomic, ?closed_list(integer))
mode name(-atomic, @closed_list(integer))

Example:

| ?- name(atom, Chars).

Chars = [97, 116, 111, 109]

| ?- name(Atom, [97, 116, 111, 109]).

Atom = atom

| ?- name(Atom, "atom").

Atom = atom

char_code(Atom, CharCode)

CharCode is the character code for the single character atom Atom.
mode char_code(@atom, ?integer)
mode char_code(-atom, @integer)

Example:

| ?- char_code(a, Code).

Code = 97

| ?- char_code(Char,97).

Char = a

number_chars(Integer, AtomList)

AtomList is the list of characters corresponding to the successive characters of Integer.
mode number_chars(@integer, ?closed_list(atom))
mode number_chars(-integer, @closed_list(atom))

Example:

| ?- number_chars(42, Chars).

Chars = [4, 2]

number_codes(Integer, CharCodeList)

CharCodeList is the list of character codes corresponding to the successive characters of Integer.
mode number_codes(@integer, ?closed_list(integer))
mode number_codes(-integer, @closed_list(integer))

Example:

| ?- number_codes(42, Codes).

Codes = [52, 50]

| ?- number_codes(Num, [52, 50]).

Num = 42

atom_concat(Atom1, Atom2, Atom3)

Atom3 is the atom formed by concatenating the characters of Atom1 and the characters of Atom2.
mode atom_concat(@atom, @atom, -atom)
mode atom_concat(?atom, ?atom, @atom)

Example:

| ?- atom_concat(ab, cd, Atom).

Atom = abcd

| ?- atom_concat(Atom1, Atom2, ab).

Atom1 = % the empty atom
Atom2 = ab;

Atom1 = a
Atom2 = b;

Atom1 = ab
Atom2 = ;

no

atom_concat2(Atom1, Atom2, Atom3)

Atom3 is the atom formed by concatenating the characters of Atom1 and the characters of Atom2. This is a faster version of atom_concat because of its more restricted mode.
mode atom_concat2(@atom, @atom, ?atom)

atom_length(Atom, N)

Length is the number of characters in Atom.
mode atom_length(@atom, ?integer)

Example:

| ?- atom_length(abc, Len).

Len = 3

atom_search(Atom1, Location1, Atom2, Location2)

Location2 is the position in Atom1 for the first occurrence of Atom2 with the search starting at Location1 in Atom1.
mode atom_search(@atom, @integer, @atom, ?atom)

Example:

| ?- atom_search(abab, 1, b, N).

N = 2

string_to_list(String, List)

List is the ASCII list corresponding to String.
mode string_to_list(@string, ?list(integer))
mode string_to_list(-string, @list(integer))

Example:

| ?- string_to_list("ab", L).

L = [97, 98]

| ?- string_to_list(S, [97,98]).

S = "ab"

string_to_atom(String, Atom)

Atom is the atom whose name is String.
mode string_to_list(@string, ?list(integer))
mode string_to_list(-string, @list(integer))

Example:

| ?- string_to_atom("ab", A).

A = ab

| ?- string_to_atom(S, ab).

S = "ab"

string_concat(String1, String2, String3)

String3 is the string formed by concatenating the characters of String1 and the characters of String2.
mode string_concat(@string, @string, -string)
mode string_concat(?string, ?string, @string)

Example:

| ?- string_concat("ab", "cd", String).

String = "abcd"

| ?- string_concat(String1, String2, "ab").

String1 = []
String2 = "ab";

String1 = "a"
String2 = "b";

String1 = "ab"
String2 = [];

no

string_length(String, N)

Length is the number of characters in String.
mode string_length(@string, ?integer)

Example:

| ?- string_length("abc", Len).

Len = 3

sub_string(String, Start, Length, After, SubString)

SubString is the substring of String starting at position Start and of length Length. After is the number of characters remaining in String after the end of SubString.
mode sub_string(@string, ?integer, ?integer, ?integer, ?string)

Example:

| ?- sub_string("ab", S, L, A, SS).

S = 0
L = 0
A = 2
SS = [];

S = 0
L = 1
A = 1
SS = "a";

S = 0
L = 2
A = 0
SS = "ab";

S = 1
L = 0
A = 1
SS = [];

S = 1
L = 1
A = 0
SS = "b";

S = 2
L = 0
A = 0
SS = [];

no

quantify(Quantified, Quantifier, VarList, Body)

Quantified is a quantified term composed of Quantifier, VarList , and Body.
mode quantify(?quant, ?term, ?list(term), ?term)

Example:

| ?- quantify(!!integral(0, !x) !x f(!x), Quant, Var, Body).

x = !x
Quant = integral(0, !x)
Var = [!x]
Body = f(!x)

| ?- quantify(QT, lambda, Var, Body).

QT = !!lambda Var Body
Var = Var
Body = Body
provided:

check_binder(Var, [])

quantifier(Quantified, Quantifier)

The quantifier of Quantified is Quantifier.
mode quantifier(+quant, ?term)

Example:

| ?- quantifier(!!integral(0, !x) !x f(!x), Quant).

x = !x
Quant = integral(0, !x)

bound_var(Quantified, VarList)

VarList is the bound variable list of the quantified term Quantified.
mode bound_var(+quant, ?list(term))

Example.

| ?- bound_var(!!q [!x:t, !y] f(A), Var).

x = !x
y = !y
A = A
Var = [!x : t, !y]
provided:

!y not_free_in [!x]
!x not_free_in [!y]

body(Quantified, Term)

Term is the body of the quantified term Quantified.
mode body(+quant, ?term)

Example.

| ?- body(!!q !x f(A), Body).

x = !x
A = A
Body = f(A)

collect_vars(Term, VarList)

VarList is a list of all the variables in Term.
mode collect_vars(@term, -closed_list(anyvar))

Example.

| ?- collect_vars(f(X, _Y, !x, !_y), VarList),
write(VarList), nl, fail.
[!_x0, !x, _1C3, X]

no

concat_atom(AtomList, Atom)
concat_atom(AtomList, Atom1, Atom2)

Atom2 is the atom formed by concatenating the characters of all the atomics in AtomList with Atom1 interleaving the atoms.
mode concat_atom(@closed_list(atomic), @atomic, ?atom)

Example.

| ?- concat_atom([a, b, c], Atom).

Atom = abc

| ?- concat_atom([a,b,c],'/', Atom).

Atom = a/b/c

copy_term(Term1, Term2)

Term2 is a copy of Term1 with all the variables replaced by fresh variables.
mode copy_term(@term, ?term)

Example:

| ?- copy_term(f(X,g(X,Y),Y), Term2).

X = X
Y = Y
Term2 = f(B, g(B, A), A)

get_distinct(ObVar, DistinctList)

DistinctList is the list of object variables known to be different from ObVar.
mode get_distinct(@obvar, ?closed_list(obvar))

Example.

| ?- !x not_free_in f(!y, !z), get_distinct(!x, List).

x = !x
y = !y
z = !z
List = [!z, !y]

provided:

!z not_free_in [!x]
!y not_free_in [!x]
!x not_free_in [!z, !y]

parallel_sub(TermList, ObVarList, SubList)

SubList is a list representing a single parallel substitution whose range elements are in TermList and whose domain elements are in ObVarList.
mode parallel_sub(@closed_list(term), @closed_list(obvar),
             -closed_list(compound))
mode parallel_sub(?closed_list(term), ?closed_list(obvar),
             +closed_list(compound))

Example:

| ?- parallel_sub([a, f(X)], [!x, !y], SubList).

X = X
x = !x
y = !y
SubList = [a / !x, f(X) / !y]

| ?- parallel_sub(TermList, ObVarList, [a / !x, f(X) / !y]).

TermList = [a, f(X)]
ObVarList = [!x, !y]
x = !x
X = X
y = !y

simplify_term(Term1, Term2)
simplify_term(Term1, Term2, Atom)

Term2 is the result of applying simplification to any substitution in Term1. Atom is set to true if any simplification is performed. Otherwise Atom is set to fail. Note that the Qu-Prolog interpreter calls simplify_term before printing answers.
mode simplify_term(@term, ?term)
mode simplify_term(@term, ?term, -atom)

Example:

| ?- simplify_term([a/!x]f(!x), Term2), write(Term2), nl, fail.
f(a)

no

| ?- simplify_term([a/!x]f(Var), Term2, Atom), write(Term2),
nl, write(Atom), nl, fail.
f([a/!x]Var)
true

no

| ?- simplify_term([a/!x][b/!y]f(X, !x, !y), Term2),
write(Term2), nl, fail.
f([a/!x, b/!y]X, [a/!x, b/!y]!x, b)

no

| ?- simplify_term([a/!x, B/!y]f(X, !x, !y), Term2),
write(Term2), nl, fail.
f([a/!x, B/!y]X, [a/!x, B/!y]!x, B)

no

| ?- simplify_term([a/!x]!!q !x B, Term2), write(Term2), nl, fail.
!!q !x B

no

| ?- simplify_term([a/!y]!!q !x B, Term2), write(Term2), nl, fail.
[a/!y](!!q !x B)

no

sub_atom(Atom1, Location, N, Atom2)

Atom2 is an atom which has N characters identical to the N characters of Atom1 starting at Location in Atom1.
mode sub_atom(@atom, ?integer, ?integer, ?atom)

Example:

| ?- sub_atom(atom1, 2, 2, Atom2).

Atom2 = to

| ?- sub_atom(atom1, Loc, 2, Atom2).

Loc = 1
Atom2 = at;

Loc = 2
Atom2 = to;

Loc = 3
Atom2 = om;

Loc = 4
Atom2 = m1;

no

| ?- sub_atom(atat, Loc, Num, at).

Loc = 1
Num = 2;

Loc = 3
Num = 2;

no

sub_term(Substituted, Term)

Term is Substituted with the substitution removed.
mode sub_term(+term, ?term)

Example:

| ?- sub_term([a/!x]f(A), Term).

x = x
A = A
Term = f(A)

substitution(Substituted, Substitutions)

Substitutions is the list of parallel substitutions appearing at the top-level of Substituted.
mode substitution(@term, -closed_list(closed_list(compound)))

Example:

| ?- substitution([x/!y, z/!x]f(X, g(Y), [y/!z]Z), Subs).

y = !y
x = !x
X = X
Y = Y
z = !z
Z = Z
Subs = [[x / !y, z / !x]]

substitute(Substituted, Substitutions, Term)

Substituted has Substitutions applied to Term. See substitution/2.
mode substitute(+term, ?closed_list(closed_list(compound)), ?term)
mode substitute(-term, @closed_list(closed_list(compound)), @term)

Example:

| ?- substitute(T, [[a/!x1, b/!x2], [c/!x3]], f(X)), write(T),fail.
[a/x1, b/x2][c/x3]f(X)

no

uncurry(HigherGoal, Goal)

Flatten a HigherGoal to a normal Goal.
mode uncurry(+term, ?term)

Example:

| ?- uncurry(f(a)(b),X).

X = f(a, b)

3.4.4 List Processing

This set of predicates provides some frequently used list operations. The set can be divided into two parts according to the type of list on which the predicates operate. The predicates which manipulate open lists (i.e. lists terminated with a variable) have a open_ prefix in the name. Otherwise, closed (proper) lists are assumed. When ==/2 is used for comparison instead of unification, the predicate name is suffixed with an _eq.

Predicates:

open_list(Term)

Succeed if Term is an open list.
mode open_list(@term)

Example:

| ?- open_list([a, b, c]).

no

| ?- open_list([a, b, c | Tail]).

Tail = Tail

closed_list(Term)

Succeed if Term is a closed (proper) list.
mode closed_list(@term)

Example:

| ?- closed_list([a, b, c]).

yes

| ?- closed_list([a, b, c | Tail]).

no

closed_to_open(Closed, Open)

Convert a Closed list to an Open list by appending an unbound variable.
mode closed_to_open(+closed_list(term), ?list(term))

Example:

| ?- Closed = [a, b, c], closed_to_open([a, b, c], Open),
write(Open), nl, fail.
[a, b, c|_1D0]

no

open_to_closed(List)

Convert List from an open list to a closed list by binding the tail to [].
mode open_to_closed(?closed_list(term))

Example:

| ?- Open = [a, b, c | Tail], open_to_closed(Open),
write(Open), nl, fail.
[a, b, c]

no

delete(Term, List1, List2)

List2 is List1 after deleting an instance of Term. The comparison is performed by unification.
mode delete(+term, +closed_list(term), ?closed_list(term))

Example:

| ?- delete(a, [a, b, d, a, c], List2).

List2 = [b, d, a, c];

List2 = [a, b, d, c];

no

delete_all(Term, List1, List2)

List2 is List1 after deleting all the instances of Term. The comparison is performed by unification.
mode delete_all(+term, +closed_list(term), ?closed_list(term))

Example:

| ?- delete_all(a, [a, b, d, a, c], List2).

List2 = [b, d, c];

no

intersect_list(List1, List2, List3)

List3 contains all the elements which appear in both List1 and List2. The comparison is performed by ==/2.
mode intersect_list(@closed_list(term), @closed_list(term),
            -closed_list(term))

Example:

| ?- intersect_list([a, b, d, a, c], [c, b, e, a, f], List3).

List3 = [a, b, a, c]

| ?- intersect_list([a, B, d, a, C], [C, b, e, a, f], List3).

B = B
C = C
List3 = [a, a, C]

union_list(List1, List2, List3)

List3 contains all the elements which appear in either List1 or List2. The comparison is performed by ==/2.
mode union_list(+closed_list(term), +closed_list(term),
           ?closed_list(term)

Example:

| ?- union_list([a, b, d, a, c], [c, b, e, a, f], List3).

List3 = [d, c, b, e, a, f]

| ?- union_list([a, B, d, a, C], [C, b, e, a, f], List3).

B = B
C = C
List3 = [B, d, C, b, e, a, f]

diff_list(List1, List2, List3)

List3 contains all those elements in List1 but not in List2. The comparison is performed by ==/2.
mode diff_list(+closed_list(Term), +closed_list(Term),
          ?closed_list(Term))

Example:

| ?- diff_list([a, b, d, a, c], [c, b, e, a, f], List3).

List3 = [d]

| ?- diff_list([a, B, d, a, C], [C, b, e, a, f], List3).

B = B
C = C
List3 = [B, d]

distribute(Term, List1, List2)

List2 is a list of pairs (Term, X) for each X in List1.
mode distribute(+term, +closed_list(term), ?closed_list(term))
mode distribute(?term, ?closed_list(term), +closed_list(term))

Example:

| ?- distribute(X, [a, b, c], List2).

X = X
List2 = [(X , a), (X , b), (X , c)]

| ?- distribute(Term, List1, [(A, 1), (A, 2), (A, 3)]).

Term = A
List1 = [1, 2, 3]
A = A

| ?- distribute(Term, List1, [(A, 1), (B, 2), (C, 3)]).

Term = C
List1 = [1, 2, 3]
A = C
B = C
C = C

distribute_left(Term, List1, List2)

List2 is a list of pairs (Term, X) for each X in List1.
mode distribute_left(+term, +closed_list(term),
           ?closed_list(term))
mode distribute_left(?term, ?closed_list(term),
           +closed_list(term))

Example:

| ?- distribute_left(f(G), [a, b, c], List2).

G = G
List2 = [(f(G) , a), (f(G) , b), (f(G) , c)]

distribute_right(Term, List1, List2)

List2 is a list of pairs (X, Term) for each X in List1.
mode distribute_right(+term, +closed_list(term),
            ?closed_list(term))
mode distribute_right(?term, ?closed_list(term),
            +closed_list(term))

Example:

| ?- distribute_right(term, [a, b, c], List2).

List2 = [(a , term), (b , term), (c , term)]

append(List1, List2, List3)

List3 is List1 appended to List2.
mode append(+closed_list(term), ?list(term), ?list(term))
mode append(?list(term), ?list(term), +closed_list(term))

Example:

| ?- append([a, b, c], [b, c, d], List3).

List3 = [a, b, c, b, c, d]

| ?- append([a, b, c], List2, List3).

List2 = List2
List3 = [a, b, c|List2]

| ?- append(List1, List2, [a, b, c, d]).

List1 = []
List2 = [a, b, c, d];

List1 = [a]
List2 = [b, c, d];

List1 = [a, b]
List2 = [c, d];

List1 = [a, b, c]
List2 = [d];

List1 = [a, b, c, d]
List2 = [];

no

length(List, N)

The length of List is N.
mode length(@closed_list(term), ?integer)
mode length(-closed_list(term), @integer)

Example:

| ?- length([a, b, c], Length).

Length = 3

| ?- length(List, 3).

List = [A, B, C]

| ?- length([a, b, c |Rest], 5).

Rest = [A, B]

| ?- length(List, Length).

List = []
Length = 0;

List = [A]
Length = 1;

List = [A, B]
Length = 2;

List = [A, B, C]
Length = 3

member(Term, List)

Term is an element of List. The comparison is performed by unification.
mode member(?term, ?list(term))

Example:

| ?- member(b, [a, b, c]).

yes

| ?- member(A, [a, b, c]).

A = a;

A = b;

A = c;

no

| ?- member(Term, List).

List = [Term|A];

List = [A, Term|B];

List = [A, B, Term|C];

List = [A, B, C, Term|D]

member_eq(Term, List)

Term is an element of List. The comparison is performed by ==/2.
mode member_eq(@term, @closed_list(term))

Example:

| ?- member_eq(Term, [a, b, c]).

no

| ?- member_eq(b, [a, b, c]).

yes

open_append(Open, List)

Append an open list, Open, and a closed list, Closed, to produce a new open list by instantiating the tail of Open.
mode open_append(+open_list(term), @closed_list(term))

Example:

| ?- List = [1, 2 | Tail], open_append(List, [3, 4]).

List = [1, 2, 3, 4|A]
Tail = [3, 4|A]

open_length(List, N)

The length of the open List is N, ignoring the tail.
mode open_length(@open_list(term), -integer)
mode open_length(?open_list(term), @integer)

Example:

| ?- open_length([a, b, c | Tail], Length).

Tail = Tail
Length = 3

| ?- open_length(List, 5).

List = [A, B, C, D, E|F]

open_member(Term, Open)

Term is an element of Open. The comparison is performed by unification with existing elements only.
mode open_member(+term, +open_list(term))

Example:

| ?- open_member(b, [a, b, c | Tail]).

Tail = Tail

| ?- open_member(Term, [a, b, c | Tail]).

Term = a
Tail = Tail;

Term = b
Tail = Tail;

Term = c
Tail = Tail;

no

| ?- open_member(Term, List).

no

open_member_eq(Term, Open)

Term is an element of Open. The comparison is performed by ==/2. mode open_member_eq(@term, @open_list(term))

Example:

| ?- open_member_eq(Term, [a, b, c | Tail]).

no

| ?- open_member_eq(b, [a, b, c | Tail]).

Rest = Rest

open_tail(Open, Variable)

Variable is the tail of the open list, Open.

mode open_tail(+open_list(term), -var)

Example:

| ?- open_tail([a, b, c | Tail], Var).

Tail = Var
Var = Var

remove_duplicates(List1, List2)

List2 is List1 without duplicates.
mode remove_duplicates(@closed_list(term), ?closed_list(term))

Example:

| ?- remove_duplicates([a, b, d, a, c], List2).

List2 = [b, d, a, c]

| ?- remove_duplicates([a, B, c, a, B, C], List2).

B = B
C = C
List2 = [c, a, B, C]

reverse(List1, List2)

List2 is the reverse of List1. The comparison is performed by ==/2.
mode reverse(+closed_list(term), ?closed_list(term))

Example:

| ?- reverse([a, b, d, a, c], List2).

List2 = [c, a, d, b, a]

search_insert(Term, Open)

Search through Open for Term. If not found, insert Term. The comparison is performed by ==/2.
mode search_insert(@term, +open_list(term))

Example:

| ?- List = [a, b, d, a, c | Tail], search_insert(d, List).

List = [a, b, d, a, c|Tail]
Tail = Tail

| ?- List = [a, b, d, a, c | Tail], search_insert(f, List).

List = [a, b, d, a, c, f|A]
Tail = [f|A]

| ?- List = [a, b, D, a, c | Tail], search_insert(D, List).

List = [a, b, D, a, c|Tail]
D = D
Tail = Tail

| ?- List = [a, b, D, a, c | Tail], search_insert(E, List).

List = [a, b, D, a, c, E|A]
D = D
Tail = [E|A]
E = E

sort(List1, List2)

List2 is the result of sorting List1 into the standard order with duplicates removed.
mode sort(@closed_list(term), -closed_list(term))

Example:

| ?- sort([a, b, d, a, c], List2).

List2 = [a, b, c, d]

3.5 All Solutions

All the solutions for Goal are collected into List according to the Template format. The solutions are obtained via backtracking.
For the examples given for each predicate below, it is assummed that the following predicate definition has been added to the system.

p(a, 1). p(a, 2). p(c, 1). p(b, 6). p(c, 4).

Predicates:

Variable^Goal

Execute Goal. It is treated the same as call(Goal). It is expected to be used only inside bagof/3, findall/3, and setof/3, where it represents existential quantification.
mode +var ^ +goal

bagof(Template, Goal, List)

List is the collection of instances of Template, which satisfy the Goal.
mode bagof(@term, @goal, ?closed_list(term))

Example:

| ?- bagof(X, p(X,Y), R).

X = X
Y = 1
R = [a, c];

X = X
Y = 2
R = [a];

X = X
Y = 4
R = [c];

X = X
Y = 6
R = [b];

no

| ?- bagof(X, Y^p(X,Y), R).

X = X
Y = Y
R = [a, a, c, b, c]

setof(Template, Goal, List)

List is the collection of instances of Template, which satisfy the Goal. Duplicates are removed and the result is sorted in the standard order.
mode setof(@term, @goal, ?closed_list(term))

Example:

| ?- setof(X, p(X,Y), R).

X = X
Y = 1
R = [a, c];

X = X
Y = 2
R = [a];

X = X
Y = 4
R = [c];

X = X
Y = 6
R = [b];

no

| ?- setof(X, Y^p(X,Y), R).

X = X
Y = Y
R = [a, b, c]

findall(Template, Goal, List)

List is the collection of instances of Template, which satisfy the Goal. Unlike bagof/3, there is an implied existential quantification of all variables not in Template.
mode findall(@term, @goal, ?closed_list(term))

Example:

| ?- findall(X, p(X,Y), R).

X = X
Y = Y
R = [a, a, c, b, c]

| ?- findall(R, setof(X, p(X,Y), R), S).

R = R
X = X
Y = Y
S = [[a, c], [a], [c], [b]]

forall(Goal, Test)

This predicate succeeds (without binding variables) iff whenever Goal succeeds, Test also succeeds.
mode forall(@goal, @goal)

Example:

| ?- forall(member(X, [1,2,3]), integer(X)).

X = X

| ?- forall(member(X, [5,4,1,3,6]), X > 2).

no

3.6 Arithmetic

These predicates perform arithmetical operations on the arguments, which are arithmetic expressions. Each expression can be a mixture of numbers, variables, and arithmetic functions. The expression must be free of unbound variables when it is evaluated.

Predicates:

Expression1 =:= Expression2

Expression1 is numerically equal to Expression2.
mode @ground =:= @ground

Term1 =\= Term2

Term1 and Term2 are not numerically equal.
mode @ground =\= @ground

Expression1 < Expression2

Expression1 is numerically less than Expression2.
mode @ground < @ground

Expression1 =< Expression2

Expression1 is numerically less than or equal to Expression2.
mode @ground =< @ground

Expression1 > Expression2

Expression1 is numerically greater than Expression2.
mode @ground > @ground

Expression1 >= Expression2

Expression1 is numerically greater than or equal to Expression2.
mode @ground >= @ground

Example:

| ?- 12 =:= 3 * 4.

| ?- 12 =\= 14.

| ?- -3 < 3.

| ?- 3*4 =< 12.

| ?- A = 12, A > 8.

| ?- A = 12, B = -2, A >= B.

between(Integer1, Integer2, N)

Integer1 <= N <= Integer2. This predicate can generate N, and may be used to provide a "for loop" like iteration driven by failure.
mode between(@integer, @integer, ?integer)

Example:

| ?- between(1, 3, A).

A = 1;

A = 2;

A = 3;

no

is(Value, Expression)

The result of evaulating Expression unifies with Value. The following operators are available.

The atoms pi and e are also available for use in arithmetic expressions.

is is an infix operator.
mode is(?number, @gcomp)
mode is(?number, @number)

Example:

| ?- A is 3 + 5.

A = 8

| ?- A is 7 / 4.

A = 1

| ?- A is 9 // 2.

A = 4

| ?- A is 7 mod 4.

A = 3

| ?- A is 2'1010 /\ 2'1001.

A = 8

| ?- A is 10 \/ 9.

A = 11

| ?- A is pi*3.5**2.

A = 38.4845

The following predicates provide uniformly distributed pseudo-random numbers.

Predicates:

srandom(Seed)

Initialize the random numbers with a seed. If Seed is supplied then that seed is used for initialization. Otherwise, a seed is generated from the current time and that seed is used for initialization and Seed is instantiated to that value.
mode srandom(?integer)

random(R)

R is unified with a random double between 0 and 1.
mode random(?double)

random(Lower, Upper, I)

I is unified with a random integer in the range [Lower, Upper].
mode random(@integer, @integer, ?integer)

irandom(I)

I is unified with a random integer.
mode irandom(?integer)

3.7 Term Expansion

When a file is consulted or compiled, every clause, fact and query within it is subject to term expansion. User term expansions are installed by defining clauses for term_expansion/2,3; the add_ and del_ predicates are provided to assist with this. Goal is a higher-order goal that will be called with two or three extra arguments: the input and output terms (Term1, Term2), and perhaps a list VariableNames of (Variable=Name) pairs for the input clause (as in read_term/[2,3]). Definite Clause Grammar (DCG) expansions are carried out automatically after user expansions.

Multi-term expansion is defined using term expansion. When multi-term expansion is active, the current set of multi-expansions will be applied repeatedly to each clause until none succeeds. It is the user's responsibility to avoid cycles; a depth limit helps identify these.

Subterm expansion is defined using term expansion. When subterm expansion is active, the current set of subterm expansions will be applied to every subterm of every clause until none succeeds. It is the user's responsibility to avoid cycles; a depth limit helps identify these.

The output of term expansion and multi-term expansion (but not of subterm expansion) may be a single term or a list of terms.

Predicates:

list_expansions

List all current term expansions, multi-term expansions and subterm expansions.

add_expansion(Goal)

Add Goal to the definition of term_expansion/2. Goal will be called with two extra arguments: the input term and the output term (or list of terms).
mode add_expansion(@goal)

add_expansion_vars(Goal)

Add Goal to the definition of term_expansion/3. Goal will be called with three extra arguments: the input term and the output term (or list of terms), and a list of Variable=Name pairs for the term being expanded.
mode add_expansion_vars(@goal)

add_multi_expansion(Goal)

Add Goal to the current set of multi-term expansions.
Also add multi_expand_term/2 to the definition of term_expansion/2 if necessary. Goal will be called with two extra arguments: the input term and the output term (or list of terms).
mode add_multi_expansion(@goal)

add_multi_expansion_vars(Goal)

Add Goal to the current set of multi-term expansions with variables and add multi_expand_term/3 to the definition of term_expansion/3 if necessary. Goal will be called with three extra arguments: the input term and the output term (or list of terms), and a list of Variable=Name pairs for the term being expanded.
mode add_multi_expansion_vars(@goal)

add_subterm_expansion(Goal)

Add Goal to the current set of subterm expansions.
Also add expand_subterms/2 to the definition of term_expansion/2 if necessary. Goal will be called with two extra arguments: the input subterm and the output subterm.
mode add_subterm_expansion(@goal)

Examples (See end of section):

| ?- assert(macro_eg(append3(A,B,C,D),
(append(A,X,D), append(B,C,X)))).

| ?- add_subterm_expansion(macro_eg).

yes

| ?- list_expansions.
term_expansion(B, A) :-
macro_eg(B, A).

yes

add_subterm_expansion_vars(Goal)

Add Goal to the current set of subterm expansions with variables, and add expand_subterms/3 to the definition of term_expansion/3 if necessary. Goal will be called with three extra arguments: the input subterm and the output subterm, and a list of Variable=Name pairs for the term being expanded.

mode add_subterm_expansion_vars(@goal)

del_expansion(Goal)

Delete Goal from the definition of term_expansion/2.
mode del_expansion(@goal)

del_expansion_vars(Goal)

Delete Goal from the definition of term_expansion/3.
mode del_expansion_vars(@goal)

del_multi_expansion(Goal)

Delete Goal from the current set of multi-term expansions, and delete multi_expand_term/2 from the definition of term_expansion/2 if it is no longer necessary.
mode del_multi_expansion(@goal)

del_multi_expansion_vars(Goal)

Delete Goal from the current set of multi-term expansions with variables, and delete multi_expand_term/3 from the definition of term_expansion/3 if it is no longer necessary.
mode del_multi_expansion_vars(@goal)

del_subterm_expansion(Goal)

Delete Goal from the current set of subterm expansions, and delete expand_subterms/2 from the definition of term_expansion/2 if it is no longer necessary.
mode del_subterm_expansion(@goal)

del_subterm_expansion_vars(Goal)

Delete Goal from the current set of subterm expansions with variables, and delete expand_subterms/3 from the definition of term_expansion/3 if it is no longer necessary.
mode del_subterm_expansion_vars(@goal)

'C'(List1, Term, List2)

List1 is connected by Term to List2.
This predicate typically appears only in preprocessed DCG rules.
mode 'C'(?list(term), ?term, ?list(term))

Example:

| ?- 'C'([a,b,c],Y,Z).

Y = a
Z = [b, c]

dcg(Rule, Clause)

Clause is the expansion of Definite Clause Grammars Rule.
mode dcg(@nonvar, ?nonvar)

Examples (See end of section):

| ?- dcg((pairing(P1 + P2) --> filler, pair(P1), pairing(P2)), X),
portray_clause(X),fail.

pairing(P1 + P2, D, A) :-
    filler(D, C),
    pair(P1, C, B),
    pairing(P2, B, A).

expand_term(Term1, Term2)
expand_term(Term1, Term2, VariableNames)

Term2 is the result of applying term expansions to Term1.
VariableNames is a list of variables and their names.
mode expand_term(+term, ?term)
mode expand_term(+term, ?term, ?closed_list(compound))

multi_expand_term(Term1, Term2)
multi_expand_term(Term1, Term2, VariableNames)

Term2 is the result of applying multi-term expansions to Term1.
VariableNames is a list of variables and their names.
mode multi_expand_term(+term, ?term)
mode multi_expand_term(+term, ?term, ?closed_list(compound))

expand_subterms(Term1, Term2)
expand_subterms(Term1, Term2, Vars)

Term2 is the result of applying subterm expansions to Term1. VariableNames is a list of variables and their names.
mode expand_subterms(+term, ?term)
mode expand_subterms(+term, ?term, ?closed_list(compound))

multi_expand_depth_limit(Limit)

The depth limit for multi-term expansion is Limit. Multi-term expansion will stop and a warning (range_exception) will be generated if this limit is exceeded in any one term. This built-in can be used to query the current limit or set a new one. The default depth is 100.
mode multi_expand_depth_limit(?integer)

subterm_expand_depth_limit(Limit)

The depth limit for subterm expansion is Limit. Subterm expansion will stop and a warning (range_exception) will be generated if this limit is exceeded in any one subterm. This built-in can be used to query the current limit or set a new one. The default depth is 100.
mode subterm_expand_depth_limit(?integer)

phrase(Rule, List1)
phrase(Rule, List1, List2)

List1 is parsed according to the DCG Rule. List2 is the remaining symbols from List1 after the parsing.
mode phrase(+nonvar, +closed_list(term))
mode phrase(+nonvar, +closed_list(term), ?closed_list(term))

Examples (See end of section):

| ?- phrase(pairing(T), "a(b(c())e)f").

T = pair(pair(pair))

| ?- phrase(pairing(T), "a(b(c())e)f(").

no

| ?- phrase(pairing(T), "a(b(c())e)f(", R).

T = pair(pair(pair))
R = [40]

The following example uses subterm expansion to achieve macro expansion.

One way to append three lists together is to write and use a predicate that appends the lists. Another way is to think of append3/4 as a macro for a pair of appends. Term expansion can then be used to expand occurrences of append3/4 within programs.

This can be achieved by first declaring the term expansion rule in a file (say expand.ql) as follows.

macro_eg(append3(A,B,C,D), (append(A,X,D), append(B,C,X))).

?-add_subterm_expansion(macro_eg).

This file can then be supplied to the Qu-Prolog compiler to term expand supplied programs. For example, assume the file expand_eg.ql contains the following definition.

p(Term, Result) :-
    extract_lists(Term, L1, L2, L3),
    append3(L1, L2, L3, L),
    process_lists(L, Result).

The compiler can then be invoked to carry out term expansion as in the following example.

qc -G -R expand expand_eg.ql

The -R switch tells the compiler to use expand.ql (or expand.qo if it is compiled) for the term expansion rules and the -G switch tells the compiler to stop after term expansion. The result is that a file expand_eg.qge will be generated that is an encoded and term expanded version of expand_eg.ql. Envoking qecat expand_eg.qge from the UNIX shell will produce the following output.

p(Term, Result) :-
    extract_lists(Term, L1, L2, L3),
    append(L1, A, L),
    append(L2, L3, A),
    process_lists(L, Result).

The example given below uses a Definite Clause Grammar to determine the bracket pairing structure of a string of characters.

The following rules define the grammar.

pairing(P1 + P2) --> filler, pair(P1), pairing(P2).
pairing(P) --> filler, pair(P), filler.

pair(pair) --> [0'(], filler, [0')].
pair(pair(P)) --> [0'(], pairing(P), [0')].

filler --> [X], {X \= 0'(, X \= 0')}, filler.
filler --> [].

When this grammar is compiled or consulted the DCG expansion will transform the grammar rules into the following Qu-Prolog rules. Note that Qu-Prolog code may appear within grammar rules as long as it is enclosed by parentheses (for example {X \= 0'(, X \= 0')}) and in this case the DCG expansion will leave this code untouched.

pairing(D + C, B, A) :-
    filler(B, E),
    pair(D, E, F),
    pairing(C, F, A),
    true.
pairing(C, B, A) :-
    filler(B, D),
    pair(C, D, E),
    filler(E, A),
    true.

filler(B, A) :-
    'C'(B, D, C),
    D \= 40,
    D \= 41,
    filler(C, A),
    true.
filler(A, A) :-
    true,
    true.

pair(pair, B, A) :-
    'C'(B, 40, C),
    filler(C, D),
    'C'(D, 41, A),
    true.
pair(pair(C), B, A) :-
    'C'(B, 40, D),
    pairing(C, D, E),
    'C'(E, 41, A),
    true.

Once this grammar is consulted or loaded then phrase/2 may be used to parse strings as in the following example.

| ?- phrase(pairing(T), "a(b(c())()e)f()g").

T = pair(pair(pair) + pair) + pair

3.8 Database

The system includes three non-backtrackable databases: the dynamic database, the record database, and the global state database.

3.8.1 Dynamic Database

Changes to the dynamic database can be achieved with the following predicates. The dynamic database is composed entirely of interpreted clauses. Clauses can be added to (asserted) or removed from (retracted) the dynamic database. The predicates cannot be applied to compiled clauses.

Clause indexing information is stored in a dynamic hash table that grows as more clauses are added. Consequently, if a dynamic predicate has many clauses then it is more efficient to declare the expected size of the predicate so that extending and rehashing is avoided. This is done with the dynamic predicate.

Predicates:

dynamic(PredicateName/Arity)
dynamic(PredicateName/Arity, Index)
dynamic(PredicateName/Arity, Index, Size)

PredicateName with Arity is declared to be an interpreted predicate, initially with no clauses.
The second argument determines the index argument - first argument indexing is the default.
The third argument declares the size of the indexing hash table for the predicate (default 4).
mode dynamic(@compound)
mode dynamic(@compound,@integer)
mode dynamic(@compound,@integer,@integer)

Example:

| ?- p(A, B).
no definition for p/2

no

| ?- dynamic(p/2).

yes

| ?- p(A, B).

no

multifile(PredicateName/Arity)

The same as dynamic(PredicateName/Arity) and is to provide an approximation to multifile as used in other Prologs.

assert(Clause)

Add the Clause to the end of the current interpreted program.
mode assert(@term)

Example:

| ?- assert((p(X) :- q(X))).

X = X

asserta(Clause)

assertz(Clause)

Add the Clause to the beginning (end) of the current interpreted program.

Example:

| ?- asserta((p(X,Y) :- q(X,Z), r(Z,Y))).

X = X
Y = Y
Z = Z

| ?- assertz((p(X,Y) :- p(Y,X)), Ref).

X = X
Y = Y
Ref = 324747

get_name(Clause, PredicateName/Arity)

The head of Clause has PredicateName and Arity.
mode get_name(@goal, ?gcomp)

Example:

| ?- get_name((p(X,Y) :- q(X,Y)), Pred).

X = X
Y = Y
Pred = p / 2

clause(Head, Body)

There is an existing clause with the given Head and Body.
mode clause(+goal, ?goal)

Examples (Continued from last):

| ?- clause((p(A,B)), Body).

A = A
B = B
Body = q(A, C) , r(C, B);

A = A
B = B
Body = p(B, A);

no

listing
listing(PredicateList)

List all interpreted predicates or only those