[m-users.] Confused my det/multi error message, full disjunction of type in place.
Sean Charles (emacstheviking)
objitsu at gmail.com
Sun Dec 4 21:35:46 AEDT 2022
Hi,
I am writing a code formatter, and I created a state object and some formatting instructions:
24 :- type fi
25 ---> nl
26 ; brace_o; brace_c % indentation gets updated
27 ; s(string)
28 ; blk(list(fi))
29 ; csv(list(fi))
30 ; ssv(list(fi))
31 ; seq(fi, list(fi))
32 .
42 :- type fstate
43 ---> fstate(
44 indent :: int,
45 tab_size :: int,
46 nl_written :: bool
47 ).
I have an aux., predicate that actually performs each instruction, but one of them, shown in bold, is giving me an error that I don't really understand and thus don't know how to get past, here is error message first:
formatter.m:059: In `write_'(in, out, in, di, uo):
formatter.m:059: error: determinism declaration not satisfied.
formatter.m:059: Declared `det', inferred `multi'.
formatter.m:059: The reason for the difference is the following.
formatter.m:061: Inside the case nl/0 of the switch on HeadVar__3:
formatter.m:061: disjunction has multiple clauses with solutions.
formatter.m:062: In clause for `write_(in, out, in, di, uo)':
formatter.m:062: in argument 1 of call to predicate `io.nl'/2:
formatter.m:062: mode error: variable `STATE_VARIABLE_IO_0' has
formatter.m:062: instantiatedness `mostly_unique',
formatter.m:062: expected instantiatedness was `unique'.
formatter.m:062: This kind of uniqueness mismatch is usually caused by doing
formatter.m:062: input/output or some other kind of destructive update in a
formatter.m:062: context where it can be backtracked over, such as the
formatter.m:062: condition of an if-then-else.
and the full predicate code, I've highlighted the offending clause in bold:
And the code, I just don't understand, as usual, what the compiler is trying to tell me. The io.nl/2 is det, so that can't fail, and presumably the field update can't fail either. And why hasn't this error been raised on all the other cases?
59 :- pred write_(fstate::in, fstate::out, fi::in, io::di, io::uo) is det.
60
61 write_(!S, nl, !IO) :-
62 io.nl(!IO),
63 !:S = !.S ^nl_written := yes.
64
65 write_(!S, brace_o, !IO) :-
66 write_(!S, s("{"), !IO),
67 !:S = !.S ^tab_size := !.S ^tab_size+1.
68 write_(!S, nl, !IO).
69
70 write_(!S, brace_c, !IO) :-
71 write_(!S, s("}"), !IO),
72 !:S = !.S ^tab_size := !.S ^tab_size-1.
73
74 write_(!S, s(Text), !IO) :-
75 io.print(Text, !IO).
76
77 write_(!S, blk(FIs), !IO) :-
78 P = (pred(FI::in, !.St::in, !:St::out, !.IO::di, !:IO::uo) is det :-
79 write_(!St, FI, !IO)
80 ),
81 list.foldl2(P, FIs, !S, !IO).
82
83 write_(!S, csv(FIs), !IO) :-
84 write_(!S, seq(s(", "), FIs), !IO).
85
86 write_(!S, ssv(FIs), !IO) :-
87 write_(!S, seq(s(" "), FIs), !IO).
88
89 write_(!_, seq(_, []), !IO).
90 write_(!S, seq(With, [ FI | FIs ]), !IO) :-
91 write_(!S, FI, !IO),
92 ( if list.is_empty(FIs) then
93 true
94 else
95 write_(!S, With, !IO),
96 write_(!S, seq(With, FIs), !IO)
97 ).
I think will be a good one to learn from!
Thanks,
Sea.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.mercurylang.org/archives/users/attachments/20221204/00f22bff/attachment.html>
More information about the users
mailing list