<div dir="ltr">OK, I read everybodies comments, read all the suggested links and I amended my code to be like so:<div><br></div><div><font face="courier new, monospace">:- pred char_type(char::in, chartype::out) is det.<br><br>char_type(Char, Type) :-<br>    (   if      Char = '(' then Type = p_open<br>        else if Char = ')' then Type = p_close<br>        else    Type = c_general<br>    ).<br></font></div><div><br></div><div>This works as desired and as expected which is great, but....understanding why! I can see that by using the if-then-else that the final else clause has no mention of Char, whereas before I had "Char = _"...    meaning that multiple solutions where available. In the polog-mercury transition docs, section 6 cuts and indexing it says:</div><div><br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">Mercury allows if-then-elses to be written not just as ‘C -> T ; E’, but also as ‘if C then T else E’. In Mercury, an if-then-else prunes away either the ‘else’ goal (if the condition succeeded) or the ‘then’ goal (if the condition failed), but if there are multiple solutions to the condition, they will all be found on backtracking, and the ‘then’ goal will be executed for each of those solutions. By contrast, an if-then-else in Prolog prunes away all solutions of the condition except the first.</blockquote><div><br></div><div>But I find this hard to decipher. I can see the equivalence between the two expression forms, that's the easier part, but I am confused where it says "but if there are multiple..." because if the if-the-else is syntactic sugar...? But it says something about pruning away the else goal or the then goal(s) etc. I think I nearly have it but I find my brain feeling like trying to climba greasy pole at time and I really really want to understand this.</div><div><br></div><div>All I seek is some clarification over why the if-then-else works as I expected it too and I can assimilate that and move on!</div><div><br></div><div>Thanks again,</div><div>Sean.</div><div><br></div><div><br></div><div><br></div></div><br><div class="gmail_quote"><div dir="ltr" class="gmail_attr">On Fri, 5 Jul 2019 at 05:17, Julian Fondren <<a href="mailto:jfondren@minimaltype.com">jfondren@minimaltype.com</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">On 2019-07-04 17:46, emacstheviking wrote:<br>
> Thanks Richard!<br>
> <br>
> That is so obvious when you see it. I am thinking like a Haskell<br>
> hacker this evening for sure.<br>
> I changed it to "cc_multi" and it compiled ANd did what I expected /<br>
> wanted.<br>
<br>
It may do you what you want, but this is by accident. It is legal for<br>
the cc_multi version of your code to report that '(' is a c_general<br>
rather than a p_open.<br>
<br>
Consider:<br>
<br>
<a href="https://mercurylang.org/information/doc-latest/mercury_ref/Semantics.html" rel="noreferrer" target="_blank">https://mercurylang.org/information/doc-latest/mercury_ref/Semantics.html</a><br>
<br>
Or this chapter of the Prolog to Mercury guide:<br>
<br>
<a href="https://mercurylang.org/information/doc-latest/mercury_trans_guide/Commits.html" rel="noreferrer" target="_blank">https://mercurylang.org/information/doc-latest/mercury_trans_guide/Commits.html</a><br>
<br>
I don't know Prolog well at all, and wouldn't've benefited from that<br>
chapter since I'm not familiar with that pattern of cuts and a<br>
catch-all, but I've run into your exact problem of wanting to say<br>
<br>
   char_type(')', p_open).<br>
   char_type('(', p_close).<br>
   char_type(_, c_general).<br>
<br>
because functional languages with pattern-matching all do it in an<br>
ordered way that permits very similar constructs. This is probably<br>
what you meant by "thinking like a Haskell hacker" but even C's<br>
switch() statement permits this sort of thing. For Mercury you can try<br>
viewing your code through the lens of the strict commutative<br>
semantics.<br>
<br>
So when looking at that code, imagine<br>
<br>
   char_type(_, c_general).<br>
   char_type(')', p_open).<br>
   char_type('(', p_close).<br>
<br>
or<br>
<br>
   char_type(')', p_open).<br>
   char_type(_, c_general).<br>
   char_type('(', p_close).<br>
<br>
or<br>
<br>
   char_type('(', p_close).<br>
   char_type(_, c_general).<br>
   char_type(')', p_open).<br>
<br>
...<br>
<br>
If any variation doesn't look like something you'd want, your original<br>
code isn't what you want either.<br>
_______________________________________________<br>
users mailing list<br>
<a href="mailto:users@lists.mercurylang.org" target="_blank">users@lists.mercurylang.org</a><br>
<a href="https://lists.mercurylang.org/listinfo/users" rel="noreferrer" target="_blank">https://lists.mercurylang.org/listinfo/users</a><br>
</blockquote></div>