From: Erik Naggum
Subject: predicates and generalized booleans
Date: 
Message-ID: <3069528322024035@naggum.no>
I'm sorry to interrupt the Java discussions with a simple Lisp question.

I needed a form that is t if a segment of an input string is empty, the
expression read from the substring if it is a complete expression, or the
bounding positions of the substring if end of file was encountered in
reading it.  I had this in mind (slightly simplified):

    (or (= start end)
        (read-from-string buffer nil nil
	   :start start
	   :end end)
        (cons start end))

but then I remembered something about generalized booleans, and looked up
`=' in ANSI X3.226.  it seems that an implementation is free to return any
non-nil value as the result of comparing two equal numbers.  now, this is
probably an academic issue, since no Common Lisp implementation I have ever
seen returns anything but t for true in such cases, so my question is not
what to do in practice, but why so many predicates were specified to return
a "generalized boolean" instead of just a "boolean".

the relevant glossary entry for "t" reads:

    t ... 1. ...  b. the canonical generalized boolean representing
    true. (Although any object other than nil is considered true as a
    generalized boolean, t is generally used when there is no special
    reason to prefer one such object over another.) ...

clearly, `=' and the like do not have any such special reasons, so what
motivated the use of "generalized boolean" instead of "boolean"?

#\Erik
-- 
I'm no longer young enough to know everything.
From: Erik Naggum
Subject: Re: predicates and generalized booleans
Date: 
Message-ID: <3069618707327233@naggum.no>
* Kent Pitman
| You've chided me too much on SGML style issues for the HyperSpec for me
| to let a comment like this pass without comment. ;-): You should do "in
| practice" what will keep your programs from breaking if you meat a new
| implementation.

(I deserved this.)

| Heh.  You had to ask...

and I'm truly happy I did, too.  thank you for a very informative answer.

| And, personally, I think relying on the identity of a truth value
| function as being the arbitrarily chosen object T is stylistically poor.

that was the weak hunch that prompted the question.  I've cleaned it up,
and now it's a separate function with a slight change to the semantics (a
substring entirely without contents (i.e., empty or whitespace only) causes
the returned value to be t; a complete object if that object is readable;
otherwise, a cons of an error condition and the appropriate literal:

    (flet ((parse-argument (start end)
	     (handler-case
		 (read-from-string buffer nil t
		   :start start
		   :end end)
	       (stream-error (eof)
		 (cons eof (make-array (- end start)
			     :element-type (array-element-type buffer)
			     :displaced-to buffer
			     :displaced-index-offset start)))))))

weird thing is, I think this has elegance, too.

#\Erik
-- 
I'm no longer young enough to know everything.