[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Multiple values for R4RS.




    There is a difference that I'm surprised you don't see.  When "pair?"
    returns #t for an object, I know that I can use "car" or "cdr" without
    causing an error.  No similar claim can be made for "accepts?".

There is an analogy that I'm surprised you don't see: :-)

Just because (pair? x) is #t, I can't guarantee that (cddr x) won't
error.

Similarly, just because (accepts? p 3) evaluates to #t I can't guarantee
that (accepts? cons 3) even if

(define (p . args)
  (apply cons args))

As another example, you would certainly say that I was being confused
if I complained about the following program signalling an error

(define (foo x y)
  (if (and (list? x) (> (length x) 1))
      (begin
        (set-cdr! x y)
        (cddr x))))

(foo (list 1 2) 'joe)

Further processing after initial invocation is not guaranteed to be
correct.  It depends on exactly what the program does.

Your argument seems to be that ACCEPTS? is an ill-defined concept
because when we actually give that many arguments the process may
still error out (for example if the types or range of the arguments
are incorrect).

Accepts? is not a general purpose error-hook.  It does not attempt to
find out whether a given process will terminate or error out.  It is
just telling me whether the signature of a given procedure object (not
the corresponding mathematical function) is such that it is legal to
give it 3 arguments.  It is almost "syntactic".

    If we decide to add "accepts?" to the language, we would have to say
    that an implementation is free to return #t if it cannot determine
    whether or not a given number of arguments is accepted by a given
    procedure.  An implementation might even define "accepts?" as:

Again, if you don't try to make it transitive, and a Turing oracle, it
is perfectly well defined whether a given procedure object accepts a
given number of arguments or not.  I would be very annoyed (and
consider the implementation to be in error) if 

(accepts? p 3) -> #t

and then

(p 'a 'b 'c) -> Error from apply: Too many (or few) arguments to p

It is perfectly fine if

(accepts? p 3) -> #t

and then

(p 'a 'b 'c) -> Error from apply: Too many (or few) arguments to q

where (eqv? p q) -> #f

The further constraint that is needed to make me happy is that

(define (check-2 n)
  (with-values
    (lambda ()
      (call-with-current-continuation
        (lambda (cont)
          (values (accepts? cont n) 'ignore))))
    (lambda (x y)
      x)))

(check-2 2) -> #t

(and (integer? m)
     (not (negative? m))
     (not (= m 2))
     (check-2 m)) -> #f

For all objects m.

Analogously for check-0, check-1, check-3, etc.