eyeprolog 1.5.61 → 1.5.63
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -2
- package/examples/cross-organization-data-sharing.pl +1 -1
- package/examples/data/README.md +1 -1
- package/examples/data/symbiotic-knowledge-graph-rules.pl +3 -3
- package/examples/deck/introduction-to-eyeprolog.md +1 -1
- package/examples/deck/symbiotic-knowledge-graphs.md +6 -6
- package/examples/dpv-odrl-purpose-mapping.pl +2 -2
- package/examples/explainable-ev-depot-configuration.pl +1 -1
- package/examples/odrl-dpv-fpv-trust-flow.pl +2 -2
- package/examples/odrl-dpv-healthcare-risk-ranked.pl +2 -2
- package/examples/odrl-dpv-risk-ranked.pl +2 -2
- package/examples/odrl-policy-advanced.pl +2 -2
- package/examples/odrl-policy.pl +2 -2
- package/examples/operational-incident-response.pl +1 -1
- package/examples/output/symbiotic-knowledge-graph.pl +2 -2
- package/examples/rdf12-annotated-claims.pl +2 -2
- package/examples/rdf12-annotation.pl +2 -2
- package/examples/rdf12-directional-language.pl +2 -2
- package/examples/rdf12-nested-triple-term.pl +2 -2
- package/examples/rdf12-trig-graph-join.pl +2 -2
- package/examples/rdf12-trig-named-graph.pl +2 -2
- package/examples/rdf12-trig-triple-term.pl +2 -2
- package/examples/rdf12-triple-term.pl +2 -2
- package/examples/sbom-vulnerability-response.pl +1 -1
- package/examples/scientific-evidence-graph.pl +1 -1
- package/examples/symbiotic-knowledge-graph.pl +4 -4
- package/package.json +1 -1
- package/src/lib/error.pl +35 -27
- package/src/lib/random.pl +14 -11
- package/src/lib/si.pl +47 -9
- package/src/library-autoload-index.js +1 -0
- package/src/standard-library.js +1 -1
- package/test/regression/cases-api.mjs +2 -2
- package/test/regression/cases-documentation-sync.mjs +4 -4
- package/test/regression/cases-regression.mjs +78 -0
- package/the-art-of-eyeprolog.md +428 -424
- package/tools/generate-predicate-reference.mjs +1 -1
- package/tools/predicate-reference.json +10 -1
- package/why-eyeprolog.md +1 -1
package/README.md
CHANGED
|
@@ -69,14 +69,15 @@ printf 'human(socrates).\nmortal(X) :- human(X).\n' |
|
|
|
69
69
|
- [Example decks](examples/deck/README.md) — explainable RDF/Prolog scenarios with reproducible roundtrips
|
|
70
70
|
- [Introduction to EyeProlog](https://eyereasoner.github.io/eyeprolog/examples/deck/introduction-to-eyeprolog) — short presentation deck for first-time audiences
|
|
71
71
|
- [Symbiotic Knowledge Graphs](https://eyereasoner.github.io/eyeprolog/examples/deck/symbiotic-knowledge-graphs) — RDF ↔ Prolog heatwave-response demo for human/AI/KG co-evolution
|
|
72
|
-
- [rdf-prolog-
|
|
72
|
+
- [rdf-prolog-interchange](https://github.com/eyereasoner/rdf-prolog-interchange) — standalone RDF 1.2 ↔ ISO Prolog bridge used by the RDF examples
|
|
73
|
+
- [RDF and Prolog: Two Standards-Based Legs](https://github.com/eyereasoner/rdf-prolog-interchange/blob/main/why-rdf-prolog.md) — why W3C RDF and ISO Prolog form the foundation
|
|
73
74
|
- [ISO conformance review](test/conformance/ISO-COMPLIANCE.md) — supported Part 1 profile
|
|
74
75
|
- [Latest Neumerkel conformity](test/conformance/NEUMERKEL-LATEST.md) — tracked result from the current live upstream inventory
|
|
75
76
|
- [Conformance report](conformance-report.md) — generated executable conformance status, local corpus summary, and known deviations
|
|
76
77
|
- [OpenRuleBench](openrulebench/README.md) — portable benchmark profile
|
|
77
78
|
## RDF, Prolog, and symbiotic knowledge graphs
|
|
78
79
|
|
|
79
|
-
EyeProlog can sit behind an RDF knowledge graph without inventing a private graph representation. [`rdf-prolog-
|
|
80
|
+
EyeProlog can sit behind an RDF knowledge graph without inventing a private graph representation. [`rdf-prolog-interchange`](https://github.com/eyereasoner/rdf-prolog-interchange) converts RDF 1.2 datasets to ordinary `rdf(Subject, Predicate, Object, Graph)` facts, EyeProlog applies portable rules, and ground `rdf/4` results can be converted back to RDF.
|
|
80
81
|
|
|
81
82
|
The checked [Symbiotic Knowledge Graphs example](examples/symbiotic-knowledge-graph.pl) uses named graphs and RDF 1.2 triple terms to distinguish trusted knowledge, AI-proposed statements, and human review. Its [wide-audience companion](https://eyereasoner.github.io/eyeprolog/examples/deck/symbiotic-knowledge-graphs) explains why this is a useful present-day software model for human/AI/KG co-evolution: RDF supplies shared semantic memory, Prolog supplies explicit deliberation, AI supplies new hypotheses, and people remain participants in meaning and judgment.
|
|
82
83
|
|
package/examples/data/README.md
CHANGED
|
@@ -4,7 +4,7 @@ This directory contains source and materialized data that support runnable examp
|
|
|
4
4
|
|
|
5
5
|
## Symbiotic Knowledge Graphs
|
|
6
6
|
|
|
7
|
-
The heatwave-response example uses [`rdf-prolog-
|
|
7
|
+
The heatwave-response example uses [`rdf-prolog-interchange`](https://github.com/eyereasoner/rdf-prolog-interchange) as its RDF boundary:
|
|
8
8
|
|
|
9
9
|
```text
|
|
10
10
|
symbiotic-knowledge-graph-input.nq
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
% Symbiotic knowledge graph rules for EyeProlog.
|
|
2
2
|
%
|
|
3
|
-
% The source rdf/4 facts above are generated by rdf-prolog-
|
|
3
|
+
% The source rdf/4 facts above are generated by rdf-prolog-interchange from
|
|
4
4
|
% symbiotic-knowledge-graph-input.nq. RDF stays the interchange and storage
|
|
5
5
|
% model; these rules provide the explicit reasoning and governance layer.
|
|
6
6
|
|
|
@@ -317,10 +317,10 @@ knowledge_exchange_fact(prolog_to_rdf, materialized_ground_rdf4).
|
|
|
317
317
|
|
|
318
318
|
pipeline_step(N, Description) :- pipeline_step_fact(N, Description).
|
|
319
319
|
pipeline_step_fact(1, 'RDF 1.2 N-Quads: named graphs keep source and governance boundaries explicit').
|
|
320
|
-
pipeline_step_fact(2, 'rdf-prolog-
|
|
320
|
+
pipeline_step_fact(2, 'rdf-prolog-interchange: RDF becomes ordinary rdf/4 Prolog facts without a solver').
|
|
321
321
|
pipeline_step_fact(3, 'EyeProlog: ISO Prolog rules validate candidates, apply review policy, and derive actions').
|
|
322
322
|
pipeline_step_fact(4, 'EyeProlog: result_rdf/4 materializes accepted knowledge and decisions as ground RDF-shaped facts').
|
|
323
|
-
pipeline_step_fact(5, 'rdf-prolog-
|
|
323
|
+
pipeline_step_fact(5, 'rdf-prolog-interchange: ground rdf/4 facts become RDF again for publication or federation').
|
|
324
324
|
|
|
325
325
|
cognitive_parallel(Prolog, Human) :- cognitive_parallel_fact(Prolog, Human).
|
|
326
326
|
cognitive_parallel_fact(fact, remembered_assertion).
|
|
@@ -166,7 +166,7 @@ Boolean constraints are compact when the domain is “on/off”, “selected/not
|
|
|
166
166
|
|
|
167
167
|
## RDF and knowledge graphs
|
|
168
168
|
|
|
169
|
-
EyeProlog pairs naturally with RDF through `rdf-prolog-
|
|
169
|
+
EyeProlog pairs naturally with RDF through `rdf-prolog-interchange`:
|
|
170
170
|
|
|
171
171
|
```text
|
|
172
172
|
RDF dataset
|
|
@@ -10,7 +10,7 @@ The demonstration does not claim that EyeProlog is a brain-computer interface. I
|
|
|
10
10
|
|
|
11
11
|
The architecture uses two small projects with deliberately separate jobs:
|
|
12
12
|
|
|
13
|
-
- [`rdf-prolog-
|
|
13
|
+
- [`rdf-prolog-interchange`](https://github.com/eyereasoner/rdf-prolog-interchange) moves RDF 1.2 datasets to and from ordinary `rdf/4` Prolog facts. It contains no Prolog solver.
|
|
14
14
|
- [EyeProlog](https://github.com/eyereasoner/eyeprolog) reasons over those facts with explicit ISO Prolog rules.
|
|
15
15
|
|
|
16
16
|
That separation is the central design choice. **RDF remains the shared interchange and publication layer; Prolog becomes the transparent reasoning layer.**
|
|
@@ -105,7 +105,7 @@ p2 confidencePercent 93
|
|
|
105
105
|
|
|
106
106
|
The embedded triple is a **statement being talked about**. It is not yet an asserted operational fact.
|
|
107
107
|
|
|
108
|
-
After `rdf-prolog-
|
|
108
|
+
After `rdf-prolog-interchange`, the same structure is an ordinary Prolog term:
|
|
109
109
|
|
|
110
110
|
```prolog
|
|
111
111
|
rdf(
|
|
@@ -246,10 +246,10 @@ That closeness makes it easier for a person to enter the machine's reasoning loo
|
|
|
246
246
|
|
|
247
247
|
Without RDF, the Prolog example could be dismissed as a hand-written toy knowledge base.
|
|
248
248
|
|
|
249
|
-
With `rdf-prolog-
|
|
249
|
+
With `rdf-prolog-interchange`, the roles are clearer:
|
|
250
250
|
|
|
251
251
|
- RDF provides Web identifiers, graph boundaries, literals, RDF 1.2 triple terms, and interoperable publication;
|
|
252
|
-
- `rdf-prolog-
|
|
252
|
+
- `rdf-prolog-interchange` preserves those structures as ordinary ISO Prolog terms;
|
|
253
253
|
- EyeProlog applies explicit rules and explores alternatives;
|
|
254
254
|
- materialized conclusions return to RDF.
|
|
255
255
|
|
|
@@ -279,7 +279,7 @@ A direct neural interface would change the input/output channel. It would not re
|
|
|
279
279
|
|
|
280
280
|
## Reproduce the roundtrip
|
|
281
281
|
|
|
282
|
-
Assuming `rdf-prolog-
|
|
282
|
+
Assuming `rdf-prolog-interchange` and EyeProlog are available on `PATH`:
|
|
283
283
|
|
|
284
284
|
```sh
|
|
285
285
|
rdf-to-prolog \
|
|
@@ -327,5 +327,5 @@ The deepest reason Prolog fits this vision is not nostalgia or syntax. It is tha
|
|
|
327
327
|
## References
|
|
328
328
|
|
|
329
329
|
- Ruben Taelman, [*Symbiotic Knowledge Graphs: A Vision for Semantic Brain-Computer Interfaces*](https://rubensworks.github.io/article-iswc2026-vision-symbiotic-knowledge-graphs/).
|
|
330
|
-
- [`eyereasoner/rdf-prolog-
|
|
330
|
+
- [`eyereasoner/rdf-prolog-interchange`](https://github.com/eyereasoner/rdf-prolog-interchange) — standalone RDF 1.2 ↔ ISO Prolog roundtripping toolkit.
|
|
331
331
|
- [`eyereasoner/eyeprolog`](https://github.com/eyereasoner/eyeprolog) — ISO Prolog reasoning and proof engine.
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
package/examples/odrl-policy.pl
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -29,10 +29,10 @@ knowledge_exchange(machine_to_human, recommendation(after_review, riverside, ope
|
|
|
29
29
|
knowledge_exchange(rdf_to_prolog, ordinary_rdf4_facts).
|
|
30
30
|
knowledge_exchange(prolog_to_rdf, materialized_ground_rdf4).
|
|
31
31
|
pipeline_step(1, 'RDF 1.2 N-Quads: named graphs keep source and governance boundaries explicit').
|
|
32
|
-
pipeline_step(2, 'rdf-prolog-
|
|
32
|
+
pipeline_step(2, 'rdf-prolog-interchange: RDF becomes ordinary rdf/4 Prolog facts without a solver').
|
|
33
33
|
pipeline_step(3, 'EyeProlog: ISO Prolog rules validate candidates, apply review policy, and derive actions').
|
|
34
34
|
pipeline_step(4, 'EyeProlog: result_rdf/4 materializes accepted knowledge and decisions as ground RDF-shaped facts').
|
|
35
|
-
pipeline_step(5, 'rdf-prolog-
|
|
35
|
+
pipeline_step(5, 'rdf-prolog-interchange: ground rdf/4 facts become RDF again for publication or federation').
|
|
36
36
|
cognitive_parallel(fact, remembered_assertion).
|
|
37
37
|
cognitive_parallel(rule, reusable_generalization).
|
|
38
38
|
cognitive_parallel(query, explicit_question).
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
% Adapted from rdf-prolog-
|
|
1
|
+
% Adapted from rdf-prolog-interchange.
|
|
2
2
|
% This standalone program combines generated RDF input with its ISO Prolog rules.
|
|
3
3
|
|
|
4
|
-
% Generated by rdf-prolog-
|
|
4
|
+
% Generated by rdf-prolog-interchange.
|
|
5
5
|
|
|
6
6
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
7
7
|
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
% Generated by rdf-prolog-
|
|
1
|
+
% Generated by rdf-prolog-interchange.
|
|
2
2
|
|
|
3
3
|
% RDF terms use rdf(Subject, Predicate, Object, Graph).
|
|
4
4
|
|
|
@@ -63,7 +63,7 @@ rdf(iri('https://example.org/city/review/r3'), iri('https://example.org/vocab/no
|
|
|
63
63
|
% Rules
|
|
64
64
|
% Symbiotic knowledge graph rules for EyeProlog.
|
|
65
65
|
%
|
|
66
|
-
% The source rdf/4 facts above are generated by rdf-prolog-
|
|
66
|
+
% The source rdf/4 facts above are generated by rdf-prolog-interchange from
|
|
67
67
|
% symbiotic-knowledge-graph-input.nq. RDF stays the interchange and storage
|
|
68
68
|
% model; these rules provide the explicit reasoning and governance layer.
|
|
69
69
|
|
|
@@ -380,10 +380,10 @@ knowledge_exchange_fact(prolog_to_rdf, materialized_ground_rdf4).
|
|
|
380
380
|
|
|
381
381
|
pipeline_step(N, Description) :- pipeline_step_fact(N, Description).
|
|
382
382
|
pipeline_step_fact(1, 'RDF 1.2 N-Quads: named graphs keep source and governance boundaries explicit').
|
|
383
|
-
pipeline_step_fact(2, 'rdf-prolog-
|
|
383
|
+
pipeline_step_fact(2, 'rdf-prolog-interchange: RDF becomes ordinary rdf/4 Prolog facts without a solver').
|
|
384
384
|
pipeline_step_fact(3, 'EyeProlog: ISO Prolog rules validate candidates, apply review policy, and derive actions').
|
|
385
385
|
pipeline_step_fact(4, 'EyeProlog: result_rdf/4 materializes accepted knowledge and decisions as ground RDF-shaped facts').
|
|
386
|
-
pipeline_step_fact(5, 'rdf-prolog-
|
|
386
|
+
pipeline_step_fact(5, 'rdf-prolog-interchange: ground rdf/4 facts become RDF again for publication or federation').
|
|
387
387
|
|
|
388
388
|
cognitive_parallel(Prolog, Human) :- cognitive_parallel_fact(Prolog, Human).
|
|
389
389
|
cognitive_parallel_fact(fact, remembered_assertion).
|
package/package.json
CHANGED
package/src/lib/error.pl
CHANGED
|
@@ -21,34 +21,39 @@
|
|
|
21
21
|
% raise site: the raise sites throw with [] and this wrapper prepends its
|
|
22
22
|
% element, so contexts stay proper lists and compose with any enclosing
|
|
23
23
|
% call_with_error_context/2 (issue #98).
|
|
24
|
+
% The context is named in exactly one place -- error__must_be_throw/1 -- so no
|
|
25
|
+
% raise site hands one over (issue #98). It is a throw helper rather than a
|
|
26
|
+
% call_with_error_context/2 wrapper because wrapping a Prolog goal in catch/3
|
|
27
|
+
% costs a child Solver on every call, and must_be/2 succeeds almost always.
|
|
24
28
|
must_be(Type, Term) :-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
29
|
+
( var(Type) -> error__must_be_throw(instantiation_error)
|
|
30
|
+
; error__must_be(Type, Term)
|
|
31
|
+
).
|
|
32
|
+
|
|
33
|
+
error__must_be_throw(Formal) :-
|
|
34
|
+
throw(error(Formal, [predicate-must_be/2])).
|
|
30
35
|
|
|
31
36
|
error__must_be(integer, Term) :- !,
|
|
32
|
-
( var(Term) -> instantiation_error
|
|
37
|
+
( var(Term) -> error__must_be_throw(instantiation_error)
|
|
33
38
|
; integer(Term) -> true
|
|
34
|
-
; type_error(integer, Term)
|
|
39
|
+
; error__must_be_throw(type_error(integer, Term))
|
|
35
40
|
).
|
|
36
41
|
error__must_be(atom, Term) :- !,
|
|
37
|
-
( var(Term) -> instantiation_error
|
|
42
|
+
( var(Term) -> error__must_be_throw(instantiation_error)
|
|
38
43
|
; atom(Term) -> true
|
|
39
|
-
; type_error(atom, Term)
|
|
44
|
+
; error__must_be_throw(type_error(atom, Term))
|
|
40
45
|
).
|
|
41
46
|
error__must_be(number, Term) :- !,
|
|
42
|
-
( var(Term) -> instantiation_error
|
|
47
|
+
( var(Term) -> error__must_be_throw(instantiation_error)
|
|
43
48
|
; number(Term) -> true
|
|
44
|
-
; type_error(number, Term)
|
|
49
|
+
; error__must_be_throw(type_error(number, Term))
|
|
45
50
|
).
|
|
46
51
|
error__must_be(var, Term) :- !,
|
|
47
52
|
( var(Term) -> true
|
|
48
53
|
; throw(error(uninstantiation_error(Term), []))
|
|
49
54
|
).
|
|
50
55
|
error__must_be(ground, Term) :- !,
|
|
51
|
-
( ground(Term) -> true ; instantiation_error ).
|
|
56
|
+
( ground(Term) -> true ; error__must_be_throw(instantiation_error) ).
|
|
52
57
|
error__must_be(acyclic, Term) :- !,
|
|
53
58
|
( acyclic_term(Term) -> true ; type_error(acyclic_term, Term) ).
|
|
54
59
|
error__must_be(list, Term) :- !,
|
|
@@ -56,23 +61,23 @@ error__must_be(list, Term) :- !,
|
|
|
56
61
|
error__must_be(list(Type), Term) :- !,
|
|
57
62
|
error__proper_list_of(Term, Type).
|
|
58
63
|
error__must_be(pair, Term) :- !,
|
|
59
|
-
( var(Term) -> instantiation_error
|
|
64
|
+
( var(Term) -> error__must_be_throw(instantiation_error)
|
|
60
65
|
; Term = _-_ -> true
|
|
61
|
-
; type_error(pair, Term)
|
|
66
|
+
; error__must_be_throw(type_error(pair, Term))
|
|
62
67
|
).
|
|
63
68
|
error__must_be(not_less_than_zero, Term) :- !,
|
|
64
69
|
must_be(integer, Term),
|
|
65
70
|
( Term >= 0 -> true ; domain_error(not_less_than_zero, Term) ).
|
|
66
71
|
error__must_be(Type, Term) :-
|
|
67
|
-
( var(Term) -> instantiation_error
|
|
68
|
-
; type_error(Type, Term)
|
|
72
|
+
( var(Term) -> error__must_be_throw(instantiation_error)
|
|
73
|
+
; error__must_be_throw(type_error(Type, Term))
|
|
69
74
|
).
|
|
70
75
|
|
|
71
76
|
error__proper_list([]) :- !.
|
|
72
77
|
error__proper_list([_|Tail]) :- !, error__proper_list(Tail).
|
|
73
78
|
error__proper_list(Term) :-
|
|
74
|
-
( var(Term) -> instantiation_error
|
|
75
|
-
; type_error(list, Term)
|
|
79
|
+
( var(Term) -> error__must_be_throw(instantiation_error)
|
|
80
|
+
; error__must_be_throw(type_error(list, Term))
|
|
76
81
|
).
|
|
77
82
|
|
|
78
83
|
error__proper_list_of([], _) :- !.
|
|
@@ -80,7 +85,7 @@ error__proper_list_of([Head|Tail], Type) :- !,
|
|
|
80
85
|
must_be(Type, Head),
|
|
81
86
|
error__proper_list_of(Tail, Type).
|
|
82
87
|
error__proper_list_of(Term, _) :-
|
|
83
|
-
( var(Term) -> instantiation_error
|
|
88
|
+
( var(Term) -> error__must_be_throw(instantiation_error)
|
|
84
89
|
; type_error(list, Term)
|
|
85
90
|
).
|
|
86
91
|
|
|
@@ -138,12 +143,15 @@ call_with_error_context(Goal, Pair) :-
|
|
|
138
143
|
( copy_term(Pair, Element),
|
|
139
144
|
throw(error(Error, [Element|Context])) )).
|
|
140
145
|
|
|
141
|
-
% The element must be a pair (issue #99).
|
|
142
|
-
% must_be
|
|
143
|
-
%
|
|
144
|
-
%
|
|
146
|
+
% The element must be a pair (issue #99). The test is inlined rather than
|
|
147
|
+
% delegated to must_be(pair, _) so that the wrapper stays independent of the
|
|
148
|
+
% rest of this module. The reported context matches what must_be(pair, _)
|
|
149
|
+
% produces.
|
|
150
|
+
% Written as indexed clauses rather than an if-then-else: this runs on every
|
|
151
|
+
% call_with_error_context/2 call, and an if-then-else costs several times what
|
|
152
|
+
% first-argument clause selection does.
|
|
153
|
+
error__require_pair(Pair) :- var(Pair), !,
|
|
154
|
+
throw(error(instantiation_error, [predicate-must_be/2])).
|
|
155
|
+
error__require_pair(_-_) :- !.
|
|
145
156
|
error__require_pair(Pair) :-
|
|
146
|
-
|
|
147
|
-
; Pair = _-_ -> true
|
|
148
|
-
; throw(error(type_error(pair, Pair), [predicate-must_be/2]))
|
|
149
|
-
).
|
|
157
|
+
throw(error(type_error(pair, Pair), [predicate-must_be/2])).
|
package/src/lib/random.pl
CHANGED
|
@@ -10,7 +10,7 @@
|
|
|
10
10
|
:- module(random, [maybe/0, maybe/1, maybe/2, random/1, random/3, random_integer/3, set_random/1]).
|
|
11
11
|
|
|
12
12
|
:- use_module(library(iso_ext), [bb_get/2, bb_put/2]).
|
|
13
|
-
|
|
13
|
+
|
|
14
14
|
|
|
15
15
|
maybe :-
|
|
16
16
|
random_integer(0, 2, 0).
|
|
@@ -31,7 +31,7 @@ random(Value) :-
|
|
|
31
31
|
% Context declared once per predicate instead of at each raise site, so the
|
|
32
32
|
% raise sites throw with [] and contexts stay proper composable lists.
|
|
33
33
|
random_integer(Lower, Upper, R) :-
|
|
34
|
-
|
|
34
|
+
random__check_integer_range(Lower, Upper),
|
|
35
35
|
Lower < Upper,
|
|
36
36
|
random__current_seed(Seed0),
|
|
37
37
|
random(Seed0, _, Seed),
|
|
@@ -39,28 +39,31 @@ random_integer(Lower, Upper, R) :-
|
|
|
39
39
|
R is Lower + Seed mod (Upper - Lower).
|
|
40
40
|
|
|
41
41
|
set_random(Seed) :-
|
|
42
|
-
|
|
42
|
+
random__set_seed(Seed).
|
|
43
|
+
|
|
44
|
+
random__throw(Formal, Predicate) :-
|
|
45
|
+
throw(error(Formal, [predicate-Predicate])).
|
|
43
46
|
|
|
44
47
|
random__check_integer_range(Lower, Upper) :-
|
|
45
|
-
( var(Lower) -> instantiation_error
|
|
46
|
-
; var(Upper) -> instantiation_error
|
|
48
|
+
( var(Lower) -> random__throw(instantiation_error, random_integer/3)
|
|
49
|
+
; var(Upper) -> random__throw(instantiation_error, random_integer/3)
|
|
47
50
|
; integer(Lower) -> true
|
|
48
|
-
; type_error(integer, Lower)
|
|
51
|
+
; random__throw(type_error(integer, Lower), random_integer/3)
|
|
49
52
|
),
|
|
50
53
|
( integer(Upper) -> true
|
|
51
|
-
; type_error(integer, Upper)
|
|
54
|
+
; random__throw(type_error(integer, Upper), random_integer/3)
|
|
52
55
|
).
|
|
53
56
|
|
|
54
57
|
random__set_seed(Seed) :-
|
|
55
|
-
( var(Seed) -> instantiation_error
|
|
58
|
+
( var(Seed) -> random__throw(instantiation_error, set_random/1)
|
|
56
59
|
; Seed = seed(S) ->
|
|
57
|
-
( var(S) -> instantiation_error
|
|
60
|
+
( var(S) -> random__throw(instantiation_error, set_random/1)
|
|
58
61
|
; integer(S) ->
|
|
59
62
|
random__random_normalize_seed(S, Normalized),
|
|
60
63
|
bb_put('$random_seed', Normalized)
|
|
61
|
-
; type_error(integer, S)
|
|
64
|
+
; random__throw(type_error(integer, S), set_random/1)
|
|
62
65
|
)
|
|
63
|
-
; type_error(random_state, Seed)
|
|
66
|
+
; random__throw(type_error(random_state, Seed), set_random/1)
|
|
64
67
|
).
|
|
65
68
|
|
|
66
69
|
random__current_seed(Seed) :- bb_get('$random_seed', Seed), !.
|
package/src/lib/si.pl
CHANGED
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
character_si/1,
|
|
9
9
|
term_si/1,
|
|
10
10
|
chars_si/1,
|
|
11
|
+
compare_si/3,
|
|
11
12
|
dif_si/2,
|
|
12
13
|
not_si/1,
|
|
13
14
|
when_si/2
|
|
@@ -16,24 +17,24 @@
|
|
|
16
17
|
:- meta_predicate(not_si(0)).
|
|
17
18
|
:- meta_predicate(when_si(+, 0)).
|
|
18
19
|
|
|
19
|
-
atom_si(A) :- ( var(A) -> throw(error(instantiation_error, atom_si/1)) ; atom(A) ).
|
|
20
|
-
integer_si(I) :- ( var(I) -> throw(error(instantiation_error, integer_si/1)) ; integer(I) ).
|
|
21
|
-
atomic_si(A) :- ( var(A) -> throw(error(instantiation_error, atomic_si/1)) ; atomic(A) ).
|
|
20
|
+
atom_si(A) :- ( var(A) -> throw(error(instantiation_error, [predicate-atom_si/1])) ; atom(A) ).
|
|
21
|
+
integer_si(I) :- ( var(I) -> throw(error(instantiation_error, [predicate-integer_si/1])) ; integer(I) ).
|
|
22
|
+
atomic_si(A) :- ( var(A) -> throw(error(instantiation_error, [predicate-atomic_si/1])) ; atomic(A) ).
|
|
22
23
|
|
|
23
24
|
list_si(List) :- si__list(List).
|
|
24
25
|
si__list([]).
|
|
25
26
|
si__list([_|Tail]) :- !, si__list(Tail).
|
|
26
27
|
si__list(Term) :-
|
|
27
|
-
( var(Term) -> throw(error(instantiation_error, list_si/1)) ; fail ).
|
|
28
|
+
( var(Term) -> throw(error(instantiation_error, [predicate-list_si/1])) ; fail ).
|
|
28
29
|
|
|
29
30
|
character_si(C) :-
|
|
30
|
-
( var(C) -> throw(error(instantiation_error, character_si/1))
|
|
31
|
+
( var(C) -> throw(error(instantiation_error, [predicate-character_si/1]))
|
|
31
32
|
; atom(C), atom_length(C, 1)
|
|
32
33
|
).
|
|
33
34
|
|
|
34
35
|
term_si(Term) :-
|
|
35
36
|
( ground(Term) -> acyclic_term(Term)
|
|
36
|
-
; throw(error(instantiation_error, term_si/1))
|
|
37
|
+
; throw(error(instantiation_error, [predicate-term_si/1]))
|
|
37
38
|
).
|
|
38
39
|
|
|
39
40
|
chars_si(Chars) :-
|
|
@@ -44,19 +45,56 @@ si__chars([C|Cs]) :- character_si(C), si__chars(Cs).
|
|
|
44
45
|
|
|
45
46
|
dif_si(X, Y) :-
|
|
46
47
|
X \== Y,
|
|
47
|
-
( X \= Y -> true ; throw(error(instantiation_error, dif_si/2)) ).
|
|
48
|
+
( X \= Y -> true ; throw(error(instantiation_error, [predicate-dif_si/2])) ).
|
|
48
49
|
|
|
49
50
|
not_si(Goal) :- term_si(Goal), \+ Goal.
|
|
50
51
|
|
|
51
52
|
when_si(Condition, Goal) :-
|
|
52
53
|
( si__condition(Condition) ->
|
|
53
54
|
( call(Condition) -> call(Goal)
|
|
54
|
-
; throw(error(instantiation_error, when_si/2)) )
|
|
55
|
+
; throw(error(instantiation_error, [predicate-when_si/2])) )
|
|
55
56
|
; throw(error(domain_error(when_condition_si, Condition), when_si/2))
|
|
56
57
|
).
|
|
57
58
|
|
|
58
|
-
si__condition(Condition) :- var(Condition), !, throw(error(instantiation_error, when_si/2)).
|
|
59
|
+
si__condition(Condition) :- var(Condition), !, throw(error(instantiation_error, [predicate-when_si/2])).
|
|
59
60
|
si__condition(ground(_)).
|
|
60
61
|
si__condition(nonvar(_)).
|
|
61
62
|
si__condition((A,B)) :- si__condition(A), si__condition(B).
|
|
62
63
|
si__condition((A;B)) :- si__condition(A), si__condition(B).
|
|
64
|
+
|
|
65
|
+
% compare_si(Order, A, B) holds when compare(Order, A, B) holds for *every*
|
|
66
|
+
% instance of A and B, and raises an instantiation_error otherwise. The point
|
|
67
|
+
% is to raise it as rarely as possible: an unbound variable only matters when
|
|
68
|
+
% it is what decides the ordering. So f(X) @< g(Y) is decided by the functor
|
|
69
|
+
% names, f(X,a) @< f(X,b) by the second arguments, and X == X gives (=), while
|
|
70
|
+
% f(a) vs f(Y) and X vs 1 are genuinely undecided.
|
|
71
|
+
compare_si(Order, A, B) :-
|
|
72
|
+
( A == B
|
|
73
|
+
-> Order = (=)
|
|
74
|
+
; si__order_decided(A, B)
|
|
75
|
+
-> compare(Order, A, B)
|
|
76
|
+
; throw(error(instantiation_error, [predicate-compare_si/3]))
|
|
77
|
+
).
|
|
78
|
+
|
|
79
|
+
% Both arguments are known to be non-identical here.
|
|
80
|
+
si__order_decided(A, B) :- ( var(A) ; var(B) ), !, fail.
|
|
81
|
+
si__order_decided(A, B) :-
|
|
82
|
+
compound(A), compound(B), !,
|
|
83
|
+
functor(A, NameA, ArityA),
|
|
84
|
+
functor(B, NameB, ArityB),
|
|
85
|
+
( ArityA =\= ArityB -> true
|
|
86
|
+
; NameA \== NameB -> true
|
|
87
|
+
; A =.. [_|ArgsA],
|
|
88
|
+
B =.. [_|ArgsB],
|
|
89
|
+
si__args_decided(ArgsA, ArgsB)
|
|
90
|
+
).
|
|
91
|
+
% Otherwise both are non-variables and at least one is atomic, so either the
|
|
92
|
+
% type order or the values themselves settle it and no instantiation can
|
|
93
|
+
% change the outcome.
|
|
94
|
+
si__order_decided(_, _).
|
|
95
|
+
|
|
96
|
+
si__args_decided([A|As], [B|Bs]) :-
|
|
97
|
+
( A == B
|
|
98
|
+
-> si__args_decided(As, Bs)
|
|
99
|
+
; si__order_decided(A, B)
|
|
100
|
+
).
|