eyeprolog 1.5.18 → 1.5.19
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/package.json
CHANGED
package/src/charsio-host.js
CHANGED
|
@@ -188,6 +188,11 @@ function writeOptions(term, env, solver) {
|
|
|
188
188
|
else if (option.name === 'double_quotes' && !solver.isoStrict) result.doubleQuotes = optionBoolean(option.args[0], env, option);
|
|
189
189
|
else throw new PrologError('domain_error(write_option)', copyResolved(option, env));
|
|
190
190
|
}
|
|
191
|
+
if (result.doubleQuotes === true) {
|
|
192
|
+
result.doubleQuotes = solver.prologFlags.get('double_quotes')?.value?.name ?? 'chars';
|
|
193
|
+
} else {
|
|
194
|
+
result.doubleQuotes = null;
|
|
195
|
+
}
|
|
191
196
|
return result;
|
|
192
197
|
}
|
|
193
198
|
|
package/src/write.js
CHANGED
|
@@ -334,7 +334,11 @@ function format(term, env, options, table, maxPriority = 1200, context = 'term')
|
|
|
334
334
|
}
|
|
335
335
|
}
|
|
336
336
|
|
|
337
|
-
if (
|
|
337
|
+
if (isCons(resolved)) {
|
|
338
|
+
// double_quotes/1 selects a character-list representation independently
|
|
339
|
+
// of operator notation. In normal mode, `||` is fixed list-splice syntax
|
|
340
|
+
// rather than an op/3 declaration, so ignore_ops(true) does not suppress
|
|
341
|
+
// an explicitly requested double-quoted proper or partial character list.
|
|
338
342
|
const quotedSplice = quotedListSplice(resolved, env, options.doubleQuotes);
|
|
339
343
|
if (quotedSplice != null && (quotedSplice.tail == null || options.doubleBar)) {
|
|
340
344
|
const prefix = writeString(quotedSplice.text);
|
|
@@ -344,18 +348,21 @@ function format(term, env, options, table, maxPriority = 1200, context = 'term')
|
|
|
344
348
|
// emitted text readable as the same term.
|
|
345
349
|
return `${prefix}||${format(quotedSplice.tail, env, options, table, 1, 'term')}`;
|
|
346
350
|
}
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
cursor =
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
351
|
+
|
|
352
|
+
if (!options.ignoreOps) {
|
|
353
|
+
const parts = [];
|
|
354
|
+
let cursor = resolved;
|
|
355
|
+
while (true) {
|
|
356
|
+
cursor = deref(cursor, env);
|
|
357
|
+
const separator = options.compact ? ',' : ', ';
|
|
358
|
+
if (isEmptyList(cursor)) return `[${parts.join(separator)}]`;
|
|
359
|
+
if (!isCons(cursor)) {
|
|
360
|
+
const tailSeparator = options.compact ? '|' : ' | ';
|
|
361
|
+
return `[${parts.join(separator)}${tailSeparator}${format(cursor, env, options, table, 999, 'argument')}]`;
|
|
362
|
+
}
|
|
363
|
+
parts.push(format(cursor.args[0], env, options, table, 999, 'argument'));
|
|
364
|
+
cursor = cursor.args[1];
|
|
356
365
|
}
|
|
357
|
-
parts.push(format(cursor.args[0], env, options, table, 999, 'argument'));
|
|
358
|
-
cursor = cursor.args[1];
|
|
359
366
|
}
|
|
360
367
|
}
|
|
361
368
|
|
|
@@ -124,7 +124,7 @@ families; `--iso-strict` is intended to remove their Part 1 interpretation.
|
|
|
124
124
|
| 5.5.9 Built-in predicates | EyeProlog libraries, CLP(Z), statistics, Part 3 `phrase/2-3`, and bundled-library autoloaded predicates | Strict registry contains only the Part 1 + Corrigenda core registry. |
|
|
125
125
|
| 5.5.10 Evaluable functors | Normal mode additionally accepts the EyeProlog evaluable atom `e`; the remaining arithmetic functors accepted by strict mode are the Part 1 + Corrigenda set. | Strict mode rejects `e/0` as non-evaluable and retains the Corrigendum arithmetic additions. **covered** — strict extension-boundary regression plus `src/iso-arithmetic.js`. |
|
|
126
126
|
| 5.5.11 Reserved atoms | None | None. |
|
|
127
|
-
| Cor.3 5.5.12 Options | Extra library/host options may exist outside core option lists | Normal mode additionally accepts the EyeProlog `write_term/2-3` options `double_quotes(true|false)` and `spacing(true|false)`. `spacing(false)` emits only lexically required separators; `spacing(true)` adds conventional layout around operators. Strict core excludes these implementation-specific extensions and accepts only the Part 1 plus Corrigendum 3 write-option surface; unknown extension options raise `domain_error(write_option,...)`. |
|
|
127
|
+
| Cor.3 5.5.12 Options | Extra library/host options may exist outside core option lists | Normal mode additionally accepts the EyeProlog `write_term/2-3` options `double_quotes(true|false)` and `spacing(true|false)`. `double_quotes(true)` is orthogonal to `ignore_ops(true)`: eligible character/code lists retain double-quoted notation while operator terms use functional notation, and the order of those distinct options does not affect the result. `spacing(false)` emits only lexically required separators; `spacing(true)` adds conventional layout around operators. Strict core excludes these implementation-specific extensions and accepts only the Part 1 plus Corrigendum 3 write-option surface; unknown extension options raise `domain_error(write_option,...)`. |
|
|
128
128
|
|
|
129
129
|
Normal mode provides documented module and DCG compatibility profiles whose
|
|
130
130
|
features overlap standardized Part 2 and Part 3 facilities. They are extensions
|
package/test/run-regression.mjs
CHANGED
|
@@ -7097,6 +7097,51 @@ function whiteBoxCases() {
|
|
|
7097
7097
|
}
|
|
7098
7098
|
},
|
|
7099
7099
|
},
|
|
7100
|
+
{
|
|
7101
|
+
name: 'double_quotes(true) remains effective with ignore_ops(true) in either option order (issue #88 follow-up)',
|
|
7102
|
+
run: () => {
|
|
7103
|
+
const source = [
|
|
7104
|
+
'emit :-',
|
|
7105
|
+
` write_term(f("ab",a+b), [double_quotes(true),ignore_ops(true),quoted(true)]), put_char('|'),`,
|
|
7106
|
+
` write_term(f("ab",a+b), [ignore_ops(true),double_quotes(true),quoted(true)]), put_char('|'),`,
|
|
7107
|
+
` write_term("ab"||tail, [double_quotes(true),ignore_ops(true)]), put_char('|'),`,
|
|
7108
|
+
` write_term("ab"||tail, [ignore_ops(true),double_quotes(true)]), put_char('|'),`,
|
|
7109
|
+
' write_term("ab", [double_quotes(false),ignore_ops(true)]).',
|
|
7110
|
+
'',
|
|
7111
|
+
].join('\n');
|
|
7112
|
+
assertEqual(
|
|
7113
|
+
run(source, { goal: 'emit' }).stdout,
|
|
7114
|
+
'f("ab",+(a,b))|f("ab",+(a,b))|"ab"||tail|"ab"||tail|.(a,.(b,[]))emit.\n',
|
|
7115
|
+
'write_term option composition',
|
|
7116
|
+
);
|
|
7117
|
+
|
|
7118
|
+
const codesSource = [
|
|
7119
|
+
'emit_codes :-',
|
|
7120
|
+
' set_prolog_flag(double_quotes, codes),',
|
|
7121
|
+
' write_term([97,955], [ignore_ops(true),double_quotes(true)]).',
|
|
7122
|
+
'',
|
|
7123
|
+
].join('\n');
|
|
7124
|
+
assertEqual(run(codesSource, { goal: 'emit_codes' }).stdout, '"aλ"emit_codes.\n',
|
|
7125
|
+
'double_quotes(codes) representation');
|
|
7126
|
+
},
|
|
7127
|
+
},
|
|
7128
|
+
{
|
|
7129
|
+
name: 'charsio write_term_to_chars composes double_quotes with ignore_ops',
|
|
7130
|
+
run: () => {
|
|
7131
|
+
const source = [
|
|
7132
|
+
':- use_module(library(charsio)).',
|
|
7133
|
+
'answer(A,B) :-',
|
|
7134
|
+
' write_term_to_chars(f("ab",a+b), [double_quotes(true),ignore_ops(true)], A),',
|
|
7135
|
+
' write_term_to_chars("ab"||tail, [ignore_ops(true),double_quotes(true)], B).',
|
|
7136
|
+
'',
|
|
7137
|
+
].join('\n');
|
|
7138
|
+
assertEqual(
|
|
7139
|
+
run(source, { goal: 'answer(A,B)' }).stdout,
|
|
7140
|
+
'answer("f(\\"ab\\",+(a,b))", "\\"ab\\"||tail").\n',
|
|
7141
|
+
'charsio output',
|
|
7142
|
+
);
|
|
7143
|
+
},
|
|
7144
|
+
},
|
|
7100
7145
|
{
|
|
7101
7146
|
name: 'REPL prints partial character lists with double-bar syntax (issue #88)',
|
|
7102
7147
|
run: () => {
|
package/the-art-of-eyeprolog.md
CHANGED
|
@@ -5482,8 +5482,12 @@ still retained where adjacent graphic tokens would otherwise merge, as in
|
|
|
5482
5482
|
`double_quotes(true|false)`: `true` lets eligible character/code lists use the
|
|
5483
5483
|
current `double_quotes` representation. Proper lists can therefore be written
|
|
5484
5484
|
as `"text"`, while a partial list such as `[a,b|Tail]` is written as
|
|
5485
|
-
`"ab"||Tail`.
|
|
5486
|
-
|
|
5485
|
+
`"ab"||Tail`. This representation choice is independent of `ignore_ops/1`: with
|
|
5486
|
+
`ignore_ops(true)`, operator terms use functional notation while an explicitly
|
|
5487
|
+
requested character/code list remains double quoted. Thus
|
|
5488
|
+
`write_term(f("ab",a+b),[quoted(true),ignore_ops(true),double_quotes(true)])`
|
|
5489
|
+
emits `f("ab",+(a,b))`. Reversing the two options has the same effect. Strict
|
|
5490
|
+
ISO mode rejects this implementation-specific write option. Normal mode also accepts the
|
|
5487
5491
|
implementation-specific boolean `spacing(true|false)` option: `false` emits
|
|
5488
5492
|
only separators required to avoid lexical ambiguity, while `true` adds
|
|
5489
5493
|
conventional layout around operators. For example,
|
|
@@ -6175,7 +6179,7 @@ the beginning. A peek does not mark the stream as past-end.
|
|
|
6175
6179
|
- **`write(+Term)`, `write(+Stream,+Term)`** — Writes readable operator notation without quoting atoms merely because quoting would be required for reparsing. Number variables are enabled.
|
|
6176
6180
|
- **`writeq(+Term)`, `writeq(+Stream,+Term)`** — Like `write`, but quotes atoms when required for unambiguous input syntax.
|
|
6177
6181
|
- **`write_canonical(+Term)`, `write_canonical(+Stream,+Term)`** — Writes quoted canonical functor notation while ignoring operators and without interpreting *$VAR/1*.
|
|
6178
|
-
- **`write_term(+Term,+Options)`, `write_term(+Stream,+Term,+Options)`** — Writes with *quoted(true or false)*, *ignore_ops(true or false)*, *numbervars(true or false)*, and *variable_names([Name=Variable,...])*. Normal mode also supports *double_quotes(true or false)* and *spacing(true or false)*.
|
|
6182
|
+
- **`write_term(+Term,+Options)`, `write_term(+Stream,+Term,+Options)`** — Writes with *quoted(true or false)*, *ignore_ops(true or false)*, *numbervars(true or false)*, and *variable_names([Name=Variable,...])*. Normal mode also supports *double_quotes(true or false)* and *spacing(true or false)*. `double_quotes(true)` remains effective with `ignore_ops(true)`: operator terms are written functionally while eligible character/code lists retain double-quoted notation, independently of option order.
|
|
6179
6183
|
|
|
6180
6184
|
Term input uses the program's current operator table and the same ISO quoted-character
|
|
6181
6185
|
syntax as source text, including backslash-terminated octal and hexadecimal
|