# Properties of modules and predicates

**URL:** <https://swi-prolog.discourse.group/t/properties-of-modules-and-predicates/2597>\
**Category:** Wiki\
**Tags:** how-to\
**Created:** [July 4, 2020, 1:53pm UTC](https://swi-prolog.discourse.group/t/properties-of-modules-and-predicates/2597 "2020-07-04T13:53:52Z")\
**Posts on this page:** 1\
**Page:** 1

<div class="post-metadata">

**Author:** ![Wiki](https://avatars.discourse-cdn.com/v4/letter/w/e8c25b/32.png) [@Wiki](https://swi-prolog.discourse.group/u/Wiki)\
**Post date:** [July 4, 2020, 1:53pm UTC](https://swi-prolog.discourse.group/t/properties-of-modules-and-predicates/2597/1 "2020-07-04T13:53:52Z")

</div>

> Note: If you have [Trust level](https://blog.discourse.org/2018/06/understanding-discourse-trust-levels/): [Basic](https://swi-prolog.discourse.group/badges/1/basic) you can edit this by clicking on the edit icon in the lower right. ![Capture](https://global.discourse-cdn.com/free1/uploads/swiprolog/original/1X/bfd4c3b77dc7f3f98ece3d5ae3202fcccb0fb8b3.png)

> Note: Do not reply to this topic; questions, concerns, comments, etc. are to be handled in  
> [Wiki Discussion: Properties of modules and predicates](https://swi-prolog.discourse.group/t/wiki-discussion-using-listing-n/2598)

* * *

The built-in predicate listing/0,1,2 from [library(listing)](https://www.swi-prolog.org/pldoc/man?section=listing) is used to list the contents of the database. It is more commonly thought of as listing facts, predicates, clauses and filtering based on module or predicate/fact name.

Using listing/0 will list the contents of the global `user` module. ([ref](https://stackoverflow.com/a/46798586/1243762))

* * *

listing/0 is the same as

```prolog
user:listing.

```

or

```prolog
listing(user:_).

```

* * *

listing/1 can be used to show the same predicate in different modules.

Note: The predicate `group` is from my own code, so this is exact predicate will not work for you.

```prolog
?- listing(group).

```

> **Example**
>
> ```prolog
> ?- listing(group).
> rfc5234:group([40|T0], T, [40|A], B) :-
> 'cwsp*'(T0, T1, A, C),
> alternation(T1, T2, C, D),
> 'cwsp*'(T2, [41|T], D, E),
> E=[41|B].
> 
> rfc5234_format_preserving:group(Structure, [40|A], B) :-
> 'cwsp*'(Before, A, C),
> alternation(Alternation, C, D),
> 'cwsp*'(After, D, E),
> E=[41|F],
> group_structure(Before,
> After,
> Alternation,
> Structure),
> B=F.
> 
> rfc5234_structure_preserving:group(Structure, [40|A], B) :-
> 'cwsp*'(_, A, C),
> alternation(Alternation, C, D),
> 'cwsp*'(_, D, E),
> E=[41|F],
> group_structure(Alternation, Structure),
> B=F.
> 
> true.
> 
> ```

* * *

To see the list of current modules loaded use current\_module/1.

```prolog
?- current_module(M).

```

> **Example**
>
> ```prolog
> ?- current_module(M).
> M = sandbox ;
> M = read_util ;
> M = error ;
> M = qsave ;
> M = swi_option ;
> M = prolog_listing ;
> M = predopts_analysis ;
> M = prolog_history ;
> M = prolog_stack ;
> M = predicate_options ;
> M = prolog ;
> M = shlib ;
> M = pce_swi_hooks ;
> M = prolog_clause ;
> M = lists ;
> M = arithmetic ;
> M = prolog_debug ;
> M = settings ;
> M = prolog_system_predicate_options ;
> M = ansi_term ;
> M = prolog_operator ;
> M = pce_expansion ;
> M = listing ;
> M = win_menu ;
> M = link_xpce ;
> M = base32 ;
> M = system ;
> M = prolog_source ;
> M = user ;
> false.
> 
> ```

* * *

Different modules can be selected for use with listing/0,1,2 using either

```prolog
<module>:listing.

```

or

```prolog
listing(<module>:_).

```

* * *

To see the list of current predicates loaded use current\_predicate/1.

> **Examples**
>
> ```prolog
> ?- aggregate_all(count,current_predicate(_),Count).
> Count = 1330.
> 
> ?- current_predicate(append/2).
> true.
> 
> ?- current_predicate(append/N).
> N = 1 ;
> N = 2 ;
> false.
> 
> ?- current_predicate(lists:Name).
> Name = prefix/2 ;
> Name = must_be/2 ;
> Name = remove_dup_keys/2 ;
> Name = numlist_/3 ;
> Name = remove_same_key/3 ;
> Name = max_list/3 ;
> Name = select/3 ;
> Name = subset/2 ;
> Name = is_set/1 ;
> Name = intersection/3 ;
> Name = nth_gen/5 ;
> Name = '$autoload'/3 ;
> Name = find_nth0/4 ;
> Name = append/2 ;
> Name = min_list/2 ;
> Name = sum_list/2 ;
> Name = min_member/2 ;
> Name = reverse/4 ;
> Name = flatten/2 ;
> Name = member_/3 ;
> Name = reverse/2 ;
> Name = proper_length/2 ;
> Name = select3_/4 ;
> Name = select/4 ;
> Name = flatten/3 ;
> Name = min_member_/3 ;
> Name = nth0/3 ;
> Name = sort/4 ;
> Name = nextto/3 ;
> Name = nth1/4 ;
> Name = number_list/3 ;
> Name = member/2 ;
> Name = min_list/3 ;
> Name = sum_list/3 ;
> Name = max_member_/3 ;
> Name = append/3 ;
> Name = subtract/3 ;
> Name = union/3 ;
> Name = list_to_set/2 ;
> Name = generate_nth/5 ;
> Name = last_/3 ;
> Name = numlist/3 ;
> Name = max_list/2 ;
> Name = nth0_det/3 ;
> Name = perm/2 ;
> Name = max_member/2 ;
> Name = nth1/3 ;
> Name = permutation/2 ;
> Name = append_/2 ;
> Name = same_length/2 ;
> Name = select4_/4 ;
> Name = last/2 ;
> Name = pairs_keys/2 ;
> Name = delete/3 ;
> Name = selectchk/4 ;
> Name = succ/2 ;
> Name = selectchk/3 ;
> Name = nth0/4 ;
> false.
> 
> ```

* * *

Different predicate/fact names can be selected using either

```prolog
<module>:listing(<predicate indicator>).

```

or

```prolog
listing(<module>:<predicate indicator>).

```

> **Examples**
>
> ```prolog
> ?- listing(lists:append/2).
> append(ListOfLists, List) :-
> must_be(list, ListOfLists),
> append_(ListOfLists, List).
> 
> true.
> 
> ?- lists:listing(append/2).
> append(ListOfLists, List) :-
> must_be(list, ListOfLists),
> append_(ListOfLists, List).
> 
> true.
> 
> ?- lists:listing(append/N).
> append(ListOfLists, List) :-
> must_be(list, ListOfLists),
> append_(ListOfLists, List).
> 
> append([], L, L).
> append([H|T], L, [H|R]) :-
> append(T, L, R).
> 
> true.
> 
> ```

* * *

Predicates have properties which can be accessed with predicate\_property/2.

> **Examples**
>
> ```prolog
> ?- aggregate_all(count,predicate_property(H,multifile),Count).
> Count = 23.
> 
> ?- aggregate_all(count,predicate_property(H,imported_from(F)),Count).
> Count = 117.
> 
> ?- predicate_property(H,multifile).
> H = expand_query(_9774, _9776, _9778, _9780) ;
> H = prolog_load_file(_10446, _10448) ;
> H = portray(_11114) ;
> H = pce_pre_expansion_hook(_11780, _11782) ;
> H = prolog_file_type(_12448, _12450) ;
> H = prolog_exception_hook(_13116, _13118, _13120, _13122) ;
> H = expand_answer(_13788, _13790) ;
> H = resource(_14456, _14458, _14460) ;
> H = message_property(_15126, _15128) ;
> H = url_path(_15794, _15796) ;
> H = term_expansion(_16462, _16464, _16466, _16468) ;
> H = message_hook(_17134, _17136, _17138) ;
> H = prolog_clause_name(_17804, _17806) ;
> H = exception(_18472, _18474, _18476) ;
> H = library_directory(_19142) ;
> H = prolog_list_goal(_19808) ;
> H = goal_expansion(_20474, _20476, _20478, _20480) ;
> H = prolog_predicate_name(_21146, _21148) ;
> H = term_expansion(_21814, _21816) ;
> H = pce_post_expansion_hook(_22482, _22484) ;
> H = file_search_path(_23150, _23152) ;
> H = goal_expansion(_23818, _23820) ;
> H = resource(_24486, _24488) ;
> false.
> 
> ?- predicate_property(PI,number_of_rules(C)),C > 1.
> PI = subset(_646, _648),
> C = 2 ;
> PI = absolute_file_name(_1694, _1696, _1698),
> C = 2 ;
> PI = print_message(_2744, _2746),
> C = 2 ;
> PI = portray(_3792),
> C = 4 ;
> PI = spy(_4838),
> C = 5 ;
> PI = prolog_file_type(_5884, _5886),
> C = 2 ;
> PI = stream_position_data(_6932, _6934, _6936),
> C = 2 ;
> PI = absolute_file_name(_7982, _7984),
> C = 3 ;
> PI = intersection(_9030, _9032, _9034),
> C = 3 ;
> PI = union(_10080, _10082, _10084),
> C = 3 ;
> PI = module_property(_11130, _11132),
> C = 3 ;
> PI = current_predicate(_12178, _12180),
> C = 4 ;
> PI = message_hook(_13226, _13228, _13230),
> C = 10 ;
> PI = source_file_property(_14276, _14278),
> C = 2 ;
> PI = prolog_list_goal(_15324),
> C = 2 ;
> PI = subtract(_16370, _16372, _16374),
> C = 3 ;
> PI = prolog_predicate_name(_17420, _17422),
> C = 2 ;
> PI = file_search_path(_18468, _18470),
> C = 15 ;
> PI = prolog_load_context(_19516, _19518),
> C = 11 ;
> PI = aggregate_all(_20564, _20566, _20568),
> C = 8 ;
> PI = flag(_21614, _21616, _21618),
> C = 2 ;
> PI = list_predicates(_22664),
> C = 2 ;
> false.
> 
> ?- predicate_property(append(A,B,C),P).
> P = interpreted ;
> P = visible ;
> P = static ;
> P = imported_from(lists) ;
> P = file('c:/program files/swipl/library/lists.pl') ;
> P = line_count(123) ;
> P = nodebug ;
> P = number_of_clauses(2) ;
> P = number_of_rules(1) ;
> P = last_modified_generation(5699) ;
> P = defined ;
> P = size(480).
> 
> ```

NB append/3 will return a result but most likely not the one you expect.  
If you see `imported_from(yall)` then this is probably not what you want.  
In other words don’t use the predicate indicator notation of `<name>/<arity>`,  
use a template form `<name>(<args>)`

> **Example**
>
> ```prolog
> ?- predicate_property(append/3,P).
> P = interpreted ;
> P = visible ;
> P = static ;
> P = imported_from(yall) ;
> P = transparent ;
> P = (meta_predicate? / 0) ;
> P = file('c:/program files/swipl/library/yall.pl') ;
> P = line_count(275) ;
> P = number_of_clauses(1) ;
> P = number_of_rules(1) ;
> P = last_modified_generation(5613) ;
> P = defined ;
> P = size(384).
> 
> ```

TODO: Create example with property `wrapped`. See: [prolog\_wrap.pl – Wrapping predicates](https://www.swi-prolog.org/pldoc/doc/_SWI_/library/prolog_wrap.pl)  
TODO: Create example with [quasiquoation](https://www.swi-prolog.org/pldoc/man?section=quasiquotations).  
TODO: Create example using jiti\_list/1  
TODO: Add [predicate\_options](https://www.swi-prolog.org/pldoc/man?section=predicate_options) examples.

* * *

Modules have properties which can be accessed with module\_property/2.

> **Examples**
>
> ```prolog
> ?- module_property(user,Property).
> Property = class(user) ;
> Property = exports([]) ;
> Property = exported_operators([]) ;
> Property = size(17296) ;
> Property = program_size(5184) ;
> Property = last_modified_generation(7106).
> 
> ?- module_property(Module,file(F)).
> Module = pce_swi_hooks,
> F = 'c:/program files/swipl/xpce/prolog/lib/swi_hooks.pl' ;
> Module = prolog_stack,
> F = 'c:/program files/swipl/library/prolog_stack.pl' ;
> Module = prolog_clause,
> F = 'c:/program files/swipl/library/prolog_clause.pl' ;
> Module = predicate_options,
> F = 'c:/program files/swipl/library/predicate_options.pl' ;
> Module = read_util,
> F = 'c:/program files/swipl/library/readutil.pl' ;
> Module = win_menu,
> F = 'c:/program files/swipl/library/win_menu.pl' ;
> Module = swi_option,
> F = 'c:/program files/swipl/library/option.pl' ;
> Module = prolog_listing,
> F = 'c:/program files/swipl/library/listing.pl' ;
> Module = prolog_operator,
> F = 'c:/program files/swipl/library/operators.pl' ;
> Module = link_xpce,
> F = 'c:/program files/swipl/swipl-win.rc' ;
> Module = prolog_system_predicate_options,
> F = 'c:/program files/swipl/library/dialect/swi/syspred_options.pl' ;
> Module = aggregate,
> F = 'c:/program files/swipl/library/aggregate.pl' ;
> Module = lists,
> F = 'c:/program files/swipl/library/lists.pl' ;
> Module = prolog_source,
> F = 'c:/program files/swipl/library/prolog_source.pl' ;
> Module = shlib,
> F = 'c:/program files/swipl/library/shlib.pl' ;
> Module = error,
> F = 'c:/program files/swipl/library/error.pl' ;
> Module = base32,
> F = 'c:/program files/swipl/library/base32.pl' ;
> Module = settings,
> F = 'c:/program files/swipl/library/settings.pl' ;
> Module = arithmetic,
> F = 'c:/program files/swipl/library/arithmetic.pl' ;
> Module = prolog_debug,
> F = 'c:/program files/swipl/library/debug.pl' ;
> Module = ansi_term,
> F = 'c:/program files/swipl/library/ansi_term.pl' ;
> Module = prolog_history,
> F = 'c:/program files/swipl/library/prolog_history.pl' ;
> false.
> 
> ?- module_property(Module,class(Class)).
> Module = pce_swi_hooks,
> Class = development ;
> Module = prolog_stack,
> Class = library ;
> Module = prolog_clause,
> Class = library ;
> Module = predicate_options,
> Class = library ;
> Module = sandbox,
> Class = user ;
> Module = read_util,
> Class = library ;
> Module = listing,
> Class = user ;
> Module = prolog,
> Class = user ;
> Module = win_menu,
> Class = library ;
> Module = swi_option,
> Class = library ;
> Module = prolog_listing,
> Class = library ;
> Module = pce_expansion,
> Class = user ;
> Module = prolog_operator,
> Class = library ;
> Module = link_xpce,
> Class = library ;
> Module = prolog_system_predicate_options,
> Class = library ;
> Module = aggregate,
> Class = library ;
> Module = lists,
> Class = library ;
> Module = prolog_source,
> Class = library ;
> Module = shlib,
> Class = library ;
> Module = error,
> Class = library ;
> Module = qsave,
> Class = user ;
> Module = Class,
> Class = system ;
> Module = base32,
> Class = library ;
> Module = settings,
> Class = library ;
> Module = arithmetic,
> Class = library ;
> Module = prolog_debug,
> Class = library ;
> Module = ansi_term,
> Class = library ;
> Module = predopts_analysis,
> Class = user ;
> Module = prolog_history,
> Class = library ;
> Module = Class, Class = user ;
> false.
> 
> ```

* * *

Some of the [Prolog flags](https://www.swi-prolog.org/pldoc/man?section=flags) can be set per module.

> **Example**
>
> ```prolog
> ?- user:current_prolog_flag(double_quotes,Value).
> Value = string.
> 
> ?- user:set_prolog_flag(double_quotes,codes).
> true.
> 
> ?- user:current_prolog_flag(double_quotes,Value).
> Value = codes.
> 
> ?- current_module(M),current_prolog_flag(M:double_quotes,Value).
> M = pce_swi_hooks,
> Value = string ;
> M = prolog_stack,
> Value = string ;
> M = prolog_clause,
> Value = string ;
> M = predicate_options,
> Value = string ;
> M = read_util,
> Value = string ;
> M = prolog,
> Value = string ;
> M = win_menu,
> Value = string ;
> M = link_xpce,
> Value = string ;
> M = prolog_system_predicate_options,
> Value = string ;
> M = shlib,
> Value = string ;
> M = qsave,
> Value = string ;
> M = system,
> Value = string ;
> M = base32,
> Value = string ;
> M = ansi_term,
> Value = string ;
> M = predopts_analysis,
> Value = string ;
> M = prolog_history,
> Value = string ;
> M = user,
> Value = codes ;
> false.
> 
> ```

* * *

Sometimes the output is very long and scrolls off the screen. To save the output to a file use [with\_output\_to\_file/2](https://www.swi-prolog.org/pack/file_details/fileutils/prolog/fileutils.pl).

> **Example**
>
> ```prolog
> ?- use_module(library(fileutils)).
> true.
> 
> % Yes you can load a module from top.
> 
> ?- with_output_to_file('C:/Users/Eric/Documents/append.listing.pl',listing(append)).
> true.
> 
> ```
> 
> append.listing.pl
> 
> ```prolog
> lists:append(ListOfLists, List) :-
> must_be(list, ListOfLists),
> append_(ListOfLists, List).
> 
> lists:append([], L, L).
> lists:append([H|T], L, [H|R]) :-
> append(T, L, R).
> 
> % Foreign: system:append/1
> 
> ```

Note: This uses package [fileutils](https://www.swi-prolog.org/pack/file_details/fileutils/prolog/fileutils.pl) which must be installed.

> **How to install package fileutils**
>
> ```prolog
> % Check to make sure it is not already installed.
> 
> ?- pack_list_installed.
> Installed packages (6):
> 
> i edcg@0.9.1.2 - Extended DCG
> i func@0.4.2 - Function application and composition
> i function_expansion@0.1.2 - Help for writing function-like macros
> i list_util@0.13.0 - Predicates for working with lists
> i quickcheck@0.3.0 - QuickCheck randomized testing
> i sldnfdraw@1.61 - SLDNF Draw is a Prolog program that draws SLDNF Trees in LaTeX
> true.
> 
> % Check to make sure it is available.
> 
> ?- pack_search(fileutils).
> % Contacting server at https://www.swi-prolog.org/pack/query ... ok
> p fileutils@0.3.5 - Utilities for reading, writing and finding files
> true.
> 
> % Install package fileutils
> 
> ?- pack_install(fileutils).
> % Contacting server at https://www.swi-prolog.org/pack/query ... ok
> Install fileutils@0.3.5 from https://raw.githubusercontent.com/samer--/prolog/master/fileutils/release/fileutils-0.3.5.tgz Y/n? 
> % Contacting server at https://www.swi-prolog.org/pack/query ...
> ok
> % "fileutils-0.3.5.tgz" was downloaded 10 times
> Package: fileutils
> Title: Utilities for reading, writing and finding files
> Installed version: 0.3.5
> Author: Samer Abdallah <s.abdallah@ucl.ac.uk>
> Download URL: https://raw.githubusercontent.com/samer--/prolog/master/fileutils/release/fileutils-0.3.5.tgz
> Install "fileutils-0.3.5.tgz" (20,606 bytes) Y/n? 
> true.
> 
> % Check to see it was installed
> 
> ?- pack_list_installed.
> Installed packages (7):
> 
> i edcg@0.9.1.2 - Extended DCG
> i fileutils@0.3.5 - Utilities for reading, writing and finding files
> i func@0.4.2 - Function application and composition
> i function_expansion@0.1.2 - Help for writing function-like macros
> i list_util@0.13.0 - Predicates for working with lists
> i quickcheck@0.3.0 - QuickCheck randomized testing
> i sldnfdraw@1.61 - SLDNF Draw is a Prolog program that draws SLDNF Trees in LaTeX
> true.
> 
> ```

* * *

Most libraries are located in the `library` directory under `current_prolog_flag(home,Value).`, e.g.

```prolog
?- current_prolog_flag(home,Value).
Value = 'c:/program files/swipl'.

C:/program files/swipl/library

```

however some libraries are not at the root level of the `library` directory but in a subdirectory. One popular library as such is `library\dcg\basics.pl`.

dcg\basics can be loaded with

```prolog
use_module(library(dcg/basics)).

```

then the module name can be found using current\_module/1, e.g. `current_module(M).` which shows that the module name for dcg/basics is `dcg_basics`.

* * *

With SWI-Prolog - [unit test](https://www.swi-prolog.org/pldoc/man?section=unitbox) using

```prolog
:- begin_tests(<name>).  
...
:- end_tests(<name>).

```

the section (test box) is converted into a module with the name `plunit_<name>`. The test in the section are proper predicates that can be listed using the constructed module name.

* * *

TODO: Add example based on [SO Q&A](https://stackoverflow.com/q/54239968/1243762)

* * *

Note: Some editors have these types of queries built-in. As I use [VSC](https://code.visualstudio.com/) (Visual Studio Code) I have to rely on using these instead.

* * *

External pages:

[Using SWI-Prolog’s modules](https://chiselapp.com/user/ttmrichter/repository/gng/doc/trunk/output/tutorials/swiplmodtut.html)
