[m-dev.] making cfloat__init/1 implicit

Fergus Henderson fjh at cs.mu.oz.au
Tue Sep 16 12:30:57 AEST 1997


Peter Schachte, you wrote:
> 
> > Currently you cannot pass a variable with inst `free' to a
> > procedure that expects an argument of inst `any'; instead
> > you must explicitly initialize it with a call to cfloat__init/1
> > or the like.
> 
> Aside:  it might be good to use for this a similar syntax to you the one you
> use for specifying a unification procedure for a type.  It seems nicer to me
> to make the user specify the `any initialization' procedure for a type, if
> there is to be one, than to use some convention about naming predicates.

Maybe when we have type classes...

> Also, having a custom unification predicate is somewhat similar to having an
> initialization predicate.

Actually I thought for a while about making the initialization predicate
just a specialized mode of unification: the '='(free -> any, free -> dead)
mode.  But I decided that that would probably be a bit too clever.

> > The patch below would fix this.  However, it turns out to
> > cause more problems than it solves.  The reason is that
> > mode analsis ends up picking the wrong modes -- it prefers
> > the semidet ones above the det ones.  This causes determinism
> > errors...
> 
> I don't understand this.  Picking the semidet mode sounds like a good thing:
> you fail earlier.  Surely it's better to pick a real mode than an implied
> mode?

Suppose you have the following two modes:

	:- mode plus(in(any), in(any), out(any)) is det.
	:- mode plus(in(any), in(any), in(any)) is semidet.

And suppose you call 'plus' with the third argument free.
The problem is that the compiler picks the semidet mode,
and inserts a call to initialize the free variable.
The semidet mode will never actually fail in this case,
but the compiler doesn't know that.

> I'd expect the best way to
> choose among several possible modes for a call would be:
> 
> 	1.  Prioritize them by determinism, in this order (best first):
> 		erroneous	% should be first for errors, last for loops
> 		failure
> 		semidet
> 		nondet		% not sure about the
> 		det		% order of these two
> 		multi.
> 	2.  Remove any modes that are strictly less instantiated on input
> 	    than other valid modes; eg, prefer an (in, in, out) mode over an
> 	    (out, in, out) mode, but not necessarily over an (out, out, in)
> 	    mode.  This is a partial order.
> 	3.  If there are still multiple possibilities, take them in 
> 	    declaration order.

Almost.  You need to swap the order of 1 & 2, and some details need
to change.

	1.  Remove any modes that are strictly less instantiated or
	    less informative on input than other valid modes; eg,
	    prefer an (in, in, out) mode over an (out, in, out) mode,
	    but not necessarily over an (out, out, in) mode,
	    and prefer a (free -> ...) mode over a (any -> ...) mode,
	    and prefer a (bound(f) -> ...) mode over a (ground -> ...) mode,
	    and prefer a (... -> dead) mode over a (... -> not dead) mode.

	    This is a partial order.

 	2.  Prioritize them by determinism, in this partial order (best first):

				erroneous
			       /       \
 			semidet		failure
		     /         \      /
 		det		multi
		     \        /
			nondet

 	3.  If there are still multiple possibilities, take them in 
 	    declaration order.

-- 
Fergus Henderson <fjh at cs.mu.oz.au>   |  "I have always known that the pursuit
WWW: <http://www.cs.mu.oz.au/~fjh>   |  of excellence is a lethal habit"
PGP: finger fjh at 128.250.37.3         |     -- the last words of T. S. Garp.



More information about the developers mailing list