From: Erik Naggum
Subject: On conditionals
Date: 
Message-ID: <3215299538573186@naggum.net>
  Many other programming languages have statements and expressions, but
  Common Lisp has not made that distinction quite as explicit, although the
  value of a lot of forms are not usually used.  Still, when we turn to the
  conditionals, it is somewhat different.  Common Lisp the Language (CLtL)
  introduces the conditionals by talking about cond being the primary Lisp
  conditional, but if being like if-then-else in other languages, it would
  be covered first.  However, there is a significant difference that has
  made me think that this is not accurate.  Lisp's if returns a value.  The
  ifs of other programming languages are generally _statements_ that do not
  return a value.  If they have a conditional that can return a value, it
  is usually very different from the usual if statement for one significant
  reason: It has to have a value for both the consequent and the alternate,
  while the traditional if forms have an optional alternate.  In Common
  Lisp, an else-less if form works because nil is useful value, but this is
  not a good thing.  The if form has some properties of both statement and
  expression.

  One question is whether a form has an implicit progn.  This is a clue
  that it is has statement nature.  So if it does not have an implicit
  progn, but only one value-returning form, this is a clue that it is an
  expression.

  One question is whether a form should be used for its value or not.  The
  forms when and unless should clearly not be used for their value.  They
  also have implicit progns.  There is no point in a progn unless you have
  other forms satisfying another clue to statement nature: their value(s)
  are discarded and ignored.

  The if form is both statement and expression, and it is neither, because
  it does not quite have either nature.  As an expression, it is not a good
  idea to leave out the alternate, even if you want that value to be nil.
  As a statement, adding explicit progns can be somewhat annoying.

  The general conditional cond also has some of this dual nature.  It has
  implicit progn, but returns values.  Leaving out the final branch is a
  known source of annoying bugs, whether it be the unexamined fall-through
  case or an unexpected nil return value.  Still, cond is the smartest of
  the conditional forms I have seen in any number of programming languages:
  a long chain of "else if" looks like whoever designed that excuse for a
  language forgot to design it for more than either-or style cases.  Also,
  the verbosity of the conditionals in inferior languages in this style
  gets in the way of the task at hand, so cond is the definite winner.

  The specialized conditionals case (with ccase and ecase) and typecase
  (with ctypecase and etypecase) cover common comparison cases that are
  easy to optimize and whose similarities would be totally obscured by a
  cond.  E.g.,, a test for (<= 0 x 99) may be significantly more expensive
  than a test for the type (integer 0 99).  A case "dispatching" on a set
  of characters may be implemented as a very fast table lookup that would
  otherwise be hard to do as efficiently.

  The one-branch conditionals when and unless might seem to be redundant,
  but they communicate something that neither if nor cond can communicate:
  A promise that there will not be any other alternatives, or that if its
  condition is not met, nothing needs to be done.  If it is merely an
  accident that there is one branch now, which might change in the future,
  do not use when or unless, because you are lying to yourself.  Both when
  and unless communicate an expectation.  I think when and unless should be
  used such that the condition is expected to be true, in which case when
  evaluates the body and unless does not.  In other words, unless says that
  when the condition is false, that is an exceptional thing, but when says
  that when the condition is false, that is nothing special.  That is, you
  should expect both (when (not/null ...)) and (unless (not/null ...)).

  There are no serious coding standards that apply to the rich set of
  Common Lisp conditionals.  I would, however, appeal to those who seek to
  use them all to their fullest not use if as a statement, but always as an
  expression with both branches specified.  Even if the alternate branch is
  nil, specify it explicitly.  (This may be read to imply that I think it
  was a mistake to make the alternate branch optional, but it was probably
  made optional because if looks so much like programming languages that
  had a statement-only if.)  While other programming languages may have an
  if statement, e.g., C, Common Lisp's if is much closer in meaning to C's
  conditional expression, ?:, which is usually not abused to chain a whole
  lot of them together as you lose track of which condition must hold to
  reach each expression.  In that case, use cond or one of the case forms
  as an expression, meaning: without using the option to include statements
  with the implicit progn in each body form, and ensure that you specify
  the value when none of the conditions or cases are met, even if it is nil.

  For the conditional statement, I would likewise appeal to those who seek
  to use the most of te language to use when and unless when there is only
  one known branch, but not use them for their value.  However, there may
  be an implicit alternate branch even when using when or unless: They may
  throw or return or signal an error.  I favor using unless for this, as
  explained above about unless being somewhat exceptional in nature.  When
  there are more than one branch in the conditional statement, use cond.
  In the statement capacity, I favor _not_ terminating it with a final
  alternate branch unless that branch includes some statements of its own,
  so as not to confuse it with an expression.  A final alternate branch
  like (t nil) tells me the value of the whole cond is used for something
  and thus I need to look for the return value for each condition.  To make
  this abundantly clear, it may be prudent in a complex form to use values
  forms explicitly, even if returning only a single value, but this, too,
  may decrease readability if it is not obviously seen as useful.

  Whareas most programming language have a single conditional statement
  and, if you are lucky, maybe a conditional expression, Common Lisp once
  again proves itself as the language that communicates with programmers
  and captures their intent through the choice of which of several forms to
  use.  Using only one form for a slew of different purposes is the same
  kind of impoverished literary style that you find in bad authors, but if
  you come from a language that has only one conditional, embrace the set
  of options you have in this new language.  It may even be true that in
  the natural language of the programmer, even be it English, the set of
  conditional expressions fit the single if-then-else form of programming
  languages (the writing styles of many programmers may indicate that they
  would appreciate a limited vocabulary so as not to feel alienated), but
  then using Common Lisp would be an opportunity to improve both styles.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.

From: Vassil Nikolov
Subject: Re: On conditionals
Date: 
Message-ID: <u7ksktudz.fsf@eskimo.com>
Just a few (minor) remarks added to a very insightful analysis.

    On Wed, 21 Nov 2001 02:45:42 GMT, Erik Naggum <····@naggum.net> said:

    [...]

    EN> Even if the alternate branch is
    EN> nil, specify it explicitly.

Precisely---if you omit the `else' part, you are not really
returning a value (even though the language is willing to make up
for it), so perhaps you want to use WHEN (or UNLESS).

    EN> (This may be read to imply
    EN> that I think it was a mistake to make the alternate branch
    EN> optional, but it was probably made optional because if
    EN> looks so much like programming languages that had a
    EN> statement-only if.)

Maybe existing programs also had to be accommodated which had been
written before the introduction of WHEN and UNLESS and which
omitted the `else' part?

    EN> While other programming languages may
    EN> have an if statement, e.g., C, Common Lisp's if is much
    EN> closer in meaning to C's conditional expression, ?:, which
    EN> is usually not abused to chain a whole lot of them together

Or, if we include rarely used languages, isn't Common Lisp's IF in
fact closest to Algol's *if*?  (As C's ?: cannot have the `else'
part omitted.  Though I admit my memory fails me as to what happens
in e.g. ``i := if b then j''---a compile-time error?)  In fact, off
the top of my head I should think that Algol 60 was the first
language where *if* names a conditional _expression_, a significant
difference from a conditional statement viewed essentially as an
abstraction hiding a couple of goto's.  (I am primarily talking
about the use of the _name_ `if'; otherwise, I don't know if Algol
or Lisp was the first to have a conditional expression, as they
were developed roughly at the same time, but Lisp had only COND in
the beginning.)

One couldn't say, though, that Algol's *if* was not `abused in
chains' (if I may borrow the expression).  By the way, there are
programmers who (in languages with C-like syntax) do not write
else-if chains, but rather stuff like

    if (FOO1) BAR1;
    if (FOO2) BAR2;

etc. where FOO1 and FOO2 will not be true at the same time.  (Not
that I like this too much.)


---Vassil.
From: Vassil Nikolov
Subject: Re: On conditionals
Date: 
Message-ID: <u6684tudo.fsf@eskimo.com>
Just a few (minor) remarks added to a very insightful analysis.

    On Wed, 21 Nov 2001 02:45:42 GMT, Erik Naggum <····@naggum.net> said:

    [...]

    EN> Even if the alternate branch is
    EN> nil, specify it explicitly.

Precisely---if you omit the `else' part, you are not really
returning a value (even though the language is willing to make up
for it), so perhaps you want to use WHEN (or UNLESS).

    EN> (This may be read to imply
    EN> that I think it was a mistake to make the alternate branch
    EN> optional, but it was probably made optional because if
    EN> looks so much like programming languages that had a
    EN> statement-only if.)

Maybe existing programs also had to be accommodated which had been
written before the introduction of WHEN and UNLESS and which
omitted the `else' part?

    EN> While other programming languages may
    EN> have an if statement, e.g., C, Common Lisp's if is much
    EN> closer in meaning to C's conditional expression, ?:, which
    EN> is usually not abused to chain a whole lot of them together

Or, if we include rarely used languages, isn't Common Lisp's IF in
fact closest to Algol's *if*?  (As C's ?: cannot have the `else'
part omitted.  Though I admit my memory fails me as to what happens
in e.g. ``i := if b then j''---a compile-time error?)  In fact, off
the top of my head I should think that Algol 60 was the first
language where *if* names a conditional _expression_, a significant
difference from a conditional statement viewed essentially as an
abstraction hiding a couple of goto's.  (I am primarily talking
about the use of the _name_ `if'; otherwise, I don't know if Algol
or Lisp was the first to have a conditional expression, as they
were developed roughly at the same time, but Lisp had only COND in
the beginning.)

One couldn't say, though, that Algol's *if* was not `abused in
chains' (if I may borrow the expression).  By the way, there are
programmers who (in languages with C-like syntax) do not write
else-if chains, but rather stuff like

    if (FOO1) BAR1;
    if (FOO2) BAR2;

etc. where FOO1 and FOO2 will not be true at the same time.  (Not
that I like this too much.)


---Vassil.
From: Vassil Nikolov
Subject: Re: On conditionals
Date: 
Message-ID: <u1yistuc3.fsf@eskimo.com>
Just a few (minor) remarks added to a very insightful analysis.

    On Wed, 21 Nov 2001 02:45:42 GMT, Erik Naggum <····@naggum.net> said:

    [...]

    EN> Even if the alternate branch is
    EN> nil, specify it explicitly.

Precisely---if you omit the `else' part, you are not really
returning a value (even though the language is willing to make up
for it), so perhaps you want to use WHEN (or UNLESS).

    EN> (This may be read to imply
    EN> that I think it was a mistake to make the alternate branch
    EN> optional, but it was probably made optional because if
    EN> looks so much like programming languages that had a
    EN> statement-only if.)

Maybe existing programs also had to be accommodated which had been
written before the introduction of WHEN and UNLESS and which
omitted the `else' part?

    EN> While other programming languages may
    EN> have an if statement, e.g., C, Common Lisp's if is much
    EN> closer in meaning to C's conditional expression, ?:, which
    EN> is usually not abused to chain a whole lot of them together

Or, if we include rarely used languages, isn't Common Lisp's IF in
fact closest to Algol's *if*?  (As C's ?: cannot have the `else'
part omitted.  Though I admit my memory fails me as to what happens
in e.g. ``i := if b then j''---a compile-time error?)  In fact, off
the top of my head I should think that Algol 60 was the first
language where *if* names a conditional _expression_, a significant
difference from a conditional statement viewed essentially as an
abstraction hiding a couple of goto's.  (I am primarily talking
about the use of the _name_ `if'; otherwise, I don't know if Algol
or Lisp was the first to have a conditional expression, as they
were developed roughly at the same time, but Lisp had only COND in
the beginning.)

One couldn't say, though, that Algol's *if* was not `abused in
chains' (if I may borrow the expression).  By the way, there are
programmers who (in languages with C-like syntax) do not write
else-if chains, but rather stuff like

    if (FOO1) BAR1;
    if (FOO2) BAR2;

etc. where FOO1 and FOO2 will not be true at the same time.  (Not
that I like this too much.)


---Vassil.
From: Espen Vestre
Subject: Re: On conditionals
Date: 
Message-ID: <w6bshwjzct.fsf@wallace.ws.nextra.no>
Erik Naggum <····@naggum.net> writes:

>   made me think that this is not accurate.  Lisp's if returns a value.  The
>   ifs of other programming languages are generally _statements_ that do not
>   return a value.  If they have a conditional that can return a value, it
>   is usually very different from the usual if statement for one significant
>   reason: It has to have a value for both the consequent and the alternate,
>   while the traditional if forms have an optional alternate. 

Is the latter true? I haven't used SIMULA for 16 years so I can't really
remember if the SIMULA "expression IF" worked that way, but certainly
the perl "expression if" does not work that way:

··@wallace:~ % perl -we 'print "yes\n" if (1);'
yes

(perl's _unless_, which can't be mentioned often enough since some people
 think lisp is the only language with such an animal, can of course also
 be used as a "expression unless").

>   One question is whether a form should be used for its value or not.  The
>   forms when and unless should clearly not be used for their value. 

I strongly disagree. I think when and unless can be perfectly well used
for their value. In general I think the Common Lisp programmer should
be free to use any form for it's value whenever that value can be given
a meaningful interpretation.
-- 
  (espen)
From: Janis Dzerins
Subject: Re: On conditionals
Date: 
Message-ID: <87adxgl4iu.fsf@asaka.latnet.lv>
Espen Vestre <·····@*do-not-spam-me*.vestre.net> writes:

> Erik Naggum <····@naggum.net> writes:
> 
> >   One question is whether a form should be used for its value or
> >   not.  The forms when and unless should clearly not be used for
> >   their value.
> 
> I strongly disagree. I think when and unless can be perfectly well
> used for their value. In general I think the Common Lisp programmer
> should be free to use any form for it's value whenever that value
> can be given a meaningful interpretation.

The point is not about legality or conformity, but about the
communication of intent. Lots of things in Common Lisp can be done in
many different ways and since the programs are written more for humans
than for computers, the programmer should choose the way that most
clearly communicates the intent (just like some people _do_ quote nil
and keywords).

If you use when or unless for value, you rely on the fact that if the
test fails they will return nil and you will use it as a meaningful
value. But this value does not appear anywhere and does not make this
explicit. Attention to detail at this level is what makes programs
beautiful and readable and approachable by non-experts in Common Lisp.

-- 
Janis Dzerins

  Eat shit -- billions of flies can't be wrong.
From: Kent M Pitman
Subject: Re: On conditionals
Date: 
Message-ID: <sfw6684s1qa.fsf@shell01.TheWorld.com>
Janis Dzerins <·····@latnet.lv> writes:

> Espen Vestre <·····@*do-not-spam-me*.vestre.net> writes:
> 
> > Erik Naggum <····@naggum.net> writes:
> > 
> > >   One question is whether a form should be used for its value or
> > >   not.  The forms when and unless should clearly not be used for
> > >   their value.
> > 
> > I strongly disagree. I think when and unless can be perfectly well
> > used for their value. In general I think the Common Lisp programmer
> > should be free to use any form for it's value whenever that value
> > can be given a meaningful interpretation.
> 
> The point is not about legality or conformity, but about the
> communication of intent. Lots of things in Common Lisp can be done in
> many different ways and since the programs are written more for humans
> than for computers, the programmer should choose the way that most
> clearly communicates the intent (just like some people _do_ quote nil
> and keywords).

But intent is the product of a set of style rules plus a set of actions
under those rules.  We have no style rule for determining whether the 
number 42 will be returned; that is done by using a construct from the
use of which it is ambiguous as to whether it returns 42 or not, plus
actually reading the code and determining what it will do.  Yet such
code is not blocked from clearly communicating whether 42 is returned.
 
Nor is it the burden of every programmer to exhaust every possible cue
with an associative nuance, so that if two constructs compute the same
value, there must be a difference in nuance between the two.  It is a
legitimate style decision to simply say "I use WHEN if there is no
alternative, and UNLESS if there is no consequent."  It is also a
legitimate style decision to code otherwise.  What matters more is to
know the convention than for us all to have the same convention,
because on the latter point we will not agree and we will war endlessly.

And certainly no one's style rules should keep him/her from seeing the
possibility that others use different rules.  Style rules are merely a
cue to help manage the probability of various choices being made.  If
one blindly infers that they assert actual meaning, one will find oneself
substantially and rightfully hampered in the ability to debug code.

> If you use when or unless for value, you rely on the fact that if the
> test fails they will return nil and you will use it as a meaningful
> value. But this value does not appear anywhere and does not make this
> explicit. Attention to detail at this level is what makes programs
> beautiful and readable and approachable by non-experts in Common Lisp.

I believe your case would be better made by asserting "I prefer the style
rule that says: ..."  Because that leaves room for others to choose their
own path without argument.  Asserting a style rule as if it were true,
or canonical, or right, or otherwise uniquely determined invites opposition
to what should be a common sense statement if presented properly.  Style
rules assert a possible and useful axis of consistency from among many
that are available to freely suggest.

Personally, my preferred style rule says not to omit values when they
are possible to provide and when a value is required.  So I might use
(IF x y) when an IF is not value-producing but (IF x y NIL) if the IF
is value producing.  But that doesn't mean that when I use (WHEN x y)
I am saying there is no value.  I choose between IF and WHEN on the
basis of whether I think there is a reasonable chance I might want to
add an alternative.  If I do, I sometimes prefer IF, whether or nto I
am actually supplying an alternative at the time.  When I use WHEN,
I usually either mean "this supplies no value" or "this supplies a value
which is either a meaningful true value, or a subordinate false value".
(Think of the vowel schwa in English.)  So, for example, I might 
commonly use:

 (defun get-property (x y)
   (when (symbolp x)
     (get x y)))

In such a place, I intend this to be read "the value of GET-PROPERTY is
the result of (GET X Y) when X is a symbol, but it really has no properties
otherwise".  This is computationally the same as, but connotationally
different than:

 (defun get-property (x y)
   (if (symbolp x)
       (get x y)
       nil))

which says "I mean to define that the value of the Y property of a
symbol X is stored on its plist when X is a symbol, and is NIL
otherwise."  The latter gives, to me, a stronger sense that I have
thought through the consequences of yielding NIL and that I think this
is the right value to return, while the former gives the sense that I
am merely saying "there really is no property list for non-symbols,
and you'll have to assume a default".  These are highly subtle
matters, but that's what style rules do: convey subtlety.  And to
understand that subtlety, one does not consult a central table of
uniquely determined subtlety, one consults the programmer (or
programmer team, when programmers happen to be of pre-agreed or
pre-ordained like mind) and then the code.

And, personally, I would rather convey an abstract subtlely, irrelevant
to the computation per se, but very relevant to the programmer, such 
as the one shown above ("non-symbols don't have plists" vs "it works for 
the values of non-symbol properties to be assumed to be NIL, the former
being a statement about the symbol, the latter a statement about the use
of the symbol's properties) than a concrete cue such as "this will get
used for value" or "this will not get used for value", because it conveys
information about how I _think_ about the program, rather than merely 
information about how I perform the rather mundane act of translating
my thoughts into code.

But I emphasize that this is merely a choice on my part, and that it 
will not by any absolute metric be possible to show it better or worse
than your choice.

To understand a wise style choice, one must understand wisdom.  Wisdom
is not a "what" question ("what do I do?", which almost precludes
choice) but a "why" question ("why would I do these various things?"
and then a willful selection among consequences in a space that is
most commonly not subject to linear ordering).
From: Espen Vestre
Subject: Re: On conditionals
Date: 
Message-ID: <w6k7wkqkjk.fsf@cartman.nextra.no>
Kent M Pitman <······@world.std.com> writes:

>  (defun get-property (x y)
>    (when (symbolp x)
>      (get x y)))
> 
> In such a place, I intend this to be read "the value of GET-PROPERTY is
> the result of (GET X Y) when X is a symbol, but it really has no properties
> otherwise".  

good example, and quite representative for the kind of context in which
I use the value of when myself!

-- 
  (espen)
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215359963689804@naggum.net>
* Kent M Pitman
> (defun get-property (x y)
>   (when (symbolp x)
>     (get x y)))

* Espen Vestre
| good example, and quite representative for the kind of context in which
| I use the value of when myself!

  This is a sort of half-breed between a statement and an expression.  I
  hate examples, because people attach too much meaning to their specifics,
  but I was trying to draw a line between statements and expressions, which
  I honestly assumed would be understood as directly value-returning forms.
  I assume from your responses that you would _not_ write

(setq foo (when bar zot))

  but _would_ write

(setq foo (whatever))

  in the presence of

(defun whatever ()
  (when bar
    zot))

  the latter of which does communicate "enough" to be defensible.  However,
  I find it very, very strange that you think this is so representative of
  using when as an expression that you strongly disagree that when and
  unless should not be used for their value.  To me, that says that you
  want to use when in let bindings and for arguments to functions, etc,
  which I think is just plain wrong.  Please let me know if you want to use
  when in the usual expression positions, and thus make a distinction
  between whole function bodies inside when and unless and using them for
  smaller expressions.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Espen Vestre
Subject: Re: On conditionals
Date: 
Message-ID: <w6pu6bajlt.fsf@cartman.nextra.no>
Erik Naggum <····@naggum.net> writes:

>   I assume from your responses that you would _not_ write
> 
> (setq foo (when bar zot))

I grepped through some thousand lines of code and found only one case
of that pattern (so maybe I actually intuitively do avoid it?)

But to me, 'when' has a very strong "silent" "otherwise nil" to it, so
I have absolutely no problems reading a statement like that.  (And
since I read 'when' that way, '(if bar zot nil)' is somewhat "noisy"
to me).

I really don't see the big advantage of reserving 'when' and 'unless'
to side-effects-only cases.
-- 
  (espen)
From: Espen Vestre
Subject: Re: On conditionals
Date: 
Message-ID: <w6y9kzp3ao.fsf@cartman.nextra.no>
Espen Vestre <·····@*do-not-spam-me*.vestre.net> writes:

> > (setq foo (when bar zot))
> 
> I grepped through some thousand lines of code and found only one case
> of that pattern (so maybe I actually intuitively do avoid it?)

After sleeping on it, I think the actual reason for the fact that such
forms are rare even if you're comfortable with using WHEN for its
value, is that in contexts where you SETF a variable which has NIL as
one of its possible values, that variable is very frequently already
_initialized_ with NIL. And that means that (when bar (setf foo zot))
is the right form... In fact I begin to suspect that the underlying
reason for this style rule may be that in good code, WHEN will
"naturally" have its most dominant usage for side effects. And this
statistical observation has then been simplified to a style rule which
disturbs me because it tries to introduce a classification of lisp
forms into two classes, a classification which I consider rather
unlispish (and I haven't touched scheme for the last 13 years, in case
you start to wonder ;-))

"All lisp forms are equalp and their values are all valuable" :-)
-- 
  (espen)
From: Kenny Tilton
Subject: Re: On conditionals
Date: 
Message-ID: <3BFC0E0B.4C7DA5D4@nyc.rr.com>
Jeez, I use when and unless for their values all the time. But then I am
an expert in lisp, I know what they return. :) I guess I am also an
expert because nil and '() look identical to me.

I think the big mistake in all this is thinking code should be readable.
It should not be. Not by non-experts, experts or even the author. it
should be understandable. anyone reading too fast to realize what when
does will not understand the code anyway. 

JF's premise in that astonishing coding standards bit is that code is
read more often than it is written. Nah, the developer spends hours and
hours on code which may never be read by anyone. Even in large teams,
when code fails the pager of the author goes off. A few years later the
whole system gets rewritten from scratch.

me, i do not have to understand my code because if i have to look at it
I rewrite it anyway.

If I cannot use when for its value, why don't we just dump the whole
language? functional programming right out the window. We can make it an
error for the when conditional to evaluate to false.

And what's this about AND and OR returning the last evaluated form's
value? talk about something not being explicit. let's get that sorted
out immediately and return t or nil, period.

<g>

kenny
clinisys





Janis Dzerins wrote:
> 
> Espen Vestre <·····@*do-not-spam-me*.vestre.net> writes:
> 
> > Erik Naggum <····@naggum.net> writes:
> >
> > >   One question is whether a form should be used for its value or
> > >   not.  The forms when and unless should clearly not be used for
> > >   their value.
> >
> > I strongly disagree. I think when and unless can be perfectly well
> > used for their value. In general I think the Common Lisp programmer
> > should be free to use any form for it's value whenever that value
> > can be given a meaningful interpretation.
> 
> The point is not about legality or conformity, but about the
> communication of intent. Lots of things in Common Lisp can be done in
> many different ways and since the programs are written more for humans
> than for computers, the programmer should choose the way that most
> clearly communicates the intent (just like some people _do_ quote nil
> and keywords).
> 
> If you use when or unless for value, you rely on the fact that if the
> test fails they will return nil and you will use it as a meaningful
> value. But this value does not appear anywhere and does not make this
> explicit. Attention to detail at this level is what makes programs
> beautiful and readable and approachable by non-experts in Common Lisp.
> 
> --
> Janis Dzerins
> 
>   Eat shit -- billions of flies can't be wrong.
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215366151466729@naggum.net>
* Kenny Tilton
| If I cannot use when for its value, why don't we just dump the whole
| language?  functional programming right out the window.  We can make it
| an error for the when conditional to evaluate to false.

  "Should not" is different from "cannot".  Grasp this and relax, please.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Dorai Sitaram
Subject: Re: On conditionals
Date: 
Message-ID: <9th7s5$3nn$1@news.gte.com>
In article <·················@nyc.rr.com>,
Kenny Tilton  <·······@nyc.rr.com> wrote:
>Jeez, I use when and unless for their values all the time. But then I am
>an expert in lisp, I know what they return. :) I guess I am also an
>expert because nil and '() look identical to me.

Since "when" (and "unless") must return a value, why
not return a meaningful value?  A return value of nil
currently does not imply that the "when" failed.
If we returned the value of the _test_, then the
result is meaningful and usable. 

--d
From: Marco Antoniotti
Subject: Re: On conditionals
Date: 
Message-ID: <y6c4rnnn5ak.fsf@octagon.mrl.nyu.edu>
····@goldshoe.gte.com (Dorai Sitaram) writes:

> In article <·················@nyc.rr.com>,
> Kenny Tilton  <·······@nyc.rr.com> wrote:
> >Jeez, I use when and unless for their values all the time. But then I am
> >an expert in lisp, I know what they return. :) I guess I am also an
> >expert because nil and '() look identical to me.
> 
> Since "when" (and "unless") must return a value, why
> not return a meaningful value?  A return value of nil
> currently does not imply that the "when" failed.
> If we returned the value of the _test_, then the
> result is meaningful and usable. 

Ahem!

* (when 3 4)
4

* (when nil 5)
NIL

Cheers

-- 
Marco Antoniotti ========================================================
NYU Courant Bioinformatics Group        tel. +1 - 212 - 998 3488
719 Broadway 12th Floor                 fax  +1 - 212 - 995 4122
New York, NY 10003, USA                 http://bioinformatics.cat.nyu.edu
                    "Hello New York! We'll do what we can!"
                           Bill Murray in `Ghostbusters'.
From: Kenny Tilton
Subject: Re: On conditionals
Date: 
Message-ID: <3BFC2EB6.3827F911@nyc.rr.com>
Dorai Sitaram wrote:
>   A return value of nil
> currently does not imply that the "when" failed.

Just to be sure I understand you, are you making the point that when
WHEN returns nil i do not know if the conditional or the consequent
returned nil? ie, it could be (when nil t) or (when t nil)?

To save an iteration at the risk of answering a straw man: that is an
interesting observation. But it should not matter; side-effects aside,
every form is a black box, the only thing a client cares about is the
result of evaluating the form, not its internals.

kenny
clinisys
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215374750296866@naggum.net>
* Dorai Sitaram
| Since "when" (and "unless") must return a value, why not return a
| meaningful value?  A return value of nil currently does not imply that
| the "when" failed.  If we returned the value of the _test_, then the
| result is meaningful and usable.

  This implies that the current return value is not meaningful, a premise
  with which I simply disagree.  Although it would be nice if when and
  unless were defined that way, I think it should be possible to return a
  value from these forms, just that it needs to be a judicious choice.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Alain Picard
Subject: Re: On conditionals
Date: 
Message-ID: <86elmrch7x.fsf@gondolin.local.net>
Kenny Tilton <·······@nyc.rr.com> writes:

> Jeez, I use when and unless for their values all the time. But then I am
> an expert in lisp, I know what they return. :) I guess I am also an
> expert because nil and '() look identical to me.
> 

That's funny, NIL and '() look totally different to me.
The former says FALSE, the latter says EMPTY LIST.

I'm very careful about their use.  Thus

(let ((bar '())
      (baz nil))
  ;; Here I fully expect BAR to be used as a list,
  ;; and BAZ as an atom.
  ...)


What's more, I used NOT to make that distinction.  It's only with
some years of practise (i.e. with _expertise_, to use your word)
that I've discovered that that distinction matters.

YMMV, of course.

-- 
It would be difficult to construe        Larry Wall, in  article
this as a feature.			 <·····················@netlabs.com>
From: Kenny Tilton
Subject: Re: On conditionals
Date: 
Message-ID: <3BFCC98F.5AB36E51@nyc.rr.com>
Alain Picard wrote:
> 
> Kenny Tilton <·······@nyc.rr.com> writes:
> 
> > Jeez, I use when and unless for their values all the time. But then I am
> > an expert in lisp, I know what they return. :) I guess I am also an
> > expert because nil and '() look identical to me.
> >
> 
> That's funny, NIL and '() look totally different to me.
> The former says FALSE, the latter says EMPTY LIST.

What does the compiler say? No Lisp implementation differentiates
between NIL and '()? So, as I see it, my mental processes should not.

Don't forget, folks, we are engaged in hand-to-hand combat with
compilers. Acknowledge their states of mind or perish. I remember
reading about SmallTalk that it had no pointers. Chya. So tell me (mr
author) is copy deep or shallow? Oops.

It would be great if some 3GL let us forget about assembly language, but
in fact every time I want to whack something from a list I must choose
between delete and remove. Explain to bubba that delete and remove from
lists are different...no way, you have to talk about implementation,
cons cells, pointers.

Now to be fair, by saying NIL and '() you are over-specifying, latching
onto conceptual differences at a finer granularity than the compiler, so
you are on solid ground. But to me that attitude is dangerous. It relies
on a fiction. Better to acknowledge the mindset of the compiler, who in
the end decides the behavior of our so-called high-level code.

kenny
clinisys
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215428049135834@naggum.net>
* Kenny Tilton
| What does the compiler say? No Lisp implementation differentiates
| between NIL and '()? So, as I see it, my mental processes should not.

  Is there no difference between (- x) and (1+ (lognot x)), either?
  How about (first x) and (car x)?  Or (ash x 3) and (* x 8)?

| Don't forget, folks, we are engaged in hand-to-hand combat with compilers.

  I have never viewed compilers this way.  Compilers are not the IRS.

| It would be great if some 3GL let us forget about assembly language, but
| in fact every time I want to whack something from a list I must choose
| between delete and remove. Explain to bubba that delete and remove from
| lists are different...no way, you have to talk about implementation, cons
| cells, pointers.

  Huh?  (let ((x '(1 2 3))) (delete 2 x) (equal x '(1 2 3))) => nil while
  (let ((x '(1 2 3))) (remove 2 x) (equal x '(1 2 3))) => t.

| Now to be fair, by saying NIL and '() you are over-specifying, latching
| onto conceptual differences at a finer granularity than the compiler, so
| you are on solid ground. But to me that attitude is dangerous. It relies
| on a fiction. Better to acknowledge the mindset of the compiler, who in
| the end decides the behavior of our so-called high-level code.

  Some of us think the specification for the compiler decides the behavior
  of the compiler.  That some things which produce the same effect but look
  different should be treated differently can be exemplified by "its" and
  "it's" and by "there" and "their" and "they're", both of which for some
  reason do not appear to be distinct to a number of American spellers.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Janis Dzerins
Subject: Re: On conditionals
Date: 
Message-ID: <87u1vmkfgd.fsf@asaka.latnet.lv>
Erik Naggum <····@naggum.net> writes:

>   That some things which produce the same effect but look different
>   should be treated differently can be exemplified by "its" and
>   "it's" and by "there" and "their" and "they're", both of which for
>   some reason do not appear to be distinct to a number of American
>   spellers.

This is nothing new. There is even a paper written with exact rules of
what should be done. Here it is:



         A Plan for the Improvement of English Spelling
                          by Mark Twain

        For example, in Year 1 that useless letter "c" would be dropped
to be replased either by "k" or "s", and likewise "x" would no longer
be part of the alphabet.  The only kase in which "c" would be retained
would be the "ch" formation, which will be dealt with later.  Year 2
might reform "w" spelling, so that "which" and "one" would take the
same konsonant, wile Year 3 might well abolish "y" replasing it with
"i" and Iear 4 might fiks the "g/j" anomali wonse and for all.
        Jenerally, then, the improvement would kontinue iear bai iear
with Iear 5 doing awai with useless double konsonants, and Iears 6-12
or so modifaiing vowlz and the rimeining voist and unvoist konsonants.
Bai Iear 15 or sou, it wud fainali bi posibl tu meik ius ov thi
ridandant letez "c", "y" and "x" -- bai now jast a memori in the maindz
ov ould doderez -- tu riplais "ch", "sh", and "th" rispektivli.
        Fainali, xen, aafte sam 20 iers ov orxogrefkl riform, wi wud
hev a lojikl, kohirnt speling in ius xrewawt xe Ingliy-spiking werld.

-- 
Janis Dzerins

  Eat shit -- billions of flies can't be wrong.
From: Kenny Tilton
Subject: Re: On conditionals
Date: 
Message-ID: <3BFD3D90.51018A4E@nyc.rr.com>
Erik Naggum wrote:
>   Or (ash x 3) and (* x 8)?

good point. ok, there is no rational basis for me not using '().

>   Huh?  (let ((x '(1 2 3))) (delete 2 x) (equal x '(1 2 3))) => nil while
>   (let ((x '(1 2 3))) (remove 2 x) (equal x '(1 2 3))) => t.

I meant the man on the street would scoff at the idea that removing
something from a list was different from deleting something from a list.
Reminds me of the time (1978) I tried to explain the Basic "x = x + 1"
to a Math teacher. He got pretty upset about that.

kenny
clinisys
From: Dorai Sitaram
Subject: Re: On conditionals
Date: 
Message-ID: <9tgcpc$3ce$1@news.gte.com>
In article <··············@wallace.ws.nextra.no>,
Espen Vestre  <·····@*do-not-spam-me*.vestre.net> wrote:
>Erik Naggum <····@naggum.net> writes:
>
>>   made me think that this is not accurate.  Lisp's if returns a value.  The
>>   ifs of other programming languages are generally _statements_ that do not
>>   return a value.  If they have a conditional that can return a value, it
>>   is usually very different from the usual if statement for one significant
>>   reason: It has to have a value for both the consequent and the alternate,
>>   while the traditional if forms have an optional alternate. 
>...
>
>>   One question is whether a form should be used for its value or not.  The
>>   forms when and unless should clearly not be used for their value. 
>
>I strongly disagree. I think when and unless can be perfectly well used
>for their value. In general I think the Common Lisp programmer should
>be free to use any form for it's value whenever that value can be given
>a meaningful interpretation.

The rules are delightfully Scheme-y, with the
difference being that in Scheme these are not "style
rules".  One has no recourse but to follow the rules,
as one cannot rely on an absent branch resolving
to #f, or even #t, or indeed any value that you can
trust.

Looks like the CL community is about to
rediscover the value (!) of the unspecified. :-)

--d 
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215360195434986@naggum.net>
* Dorai Sitaram
| Looks like the CL community is about to rediscover the value (!) of the
| unspecified. :-)

  Scheme is all wrong.  Making nil different from false is nuts, and
  letting forms have an unspecified value is also just plain wrong.

  It is important that style rules be breakable.  Enforcing them is wrong.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Thomas F. Burdick
Subject: Re: On conditionals
Date: 
Message-ID: <xcvpu6bvky7.fsf@conquest.OCF.Berkeley.EDU>
Erik Naggum <····@naggum.net> writes:

> * Dorai Sitaram
> | Looks like the CL community is about to rediscover the value (!) of the
> | unspecified. :-)
> 
>   Scheme is all wrong.  Making nil different from false is nuts, and
>   letting forms have an unspecified value is also just plain wrong.

I agree with the unspecified value part (which seems really weird for
a language with such funcitonal aspirations, too).  I'm not so sure
about false, though.  I don't like the pun that () is the same as
boolean false.  I also don't like that the empty list is a symbol.
Don't get me wrong, it's easy enough to cope with, but it's
conceptually sloppy.  I don't even see any good reason why NIL should
be false.  It's a symbol; every other symbol is true.  Of course, if
#f were a special false value, I don't know what BLOCK should return,
so that's maybe a practical argument against it.  Or, maybe it should
just return #F.  I hate the idea of someone doing something like:

  (cons 'foo (dolist ...))

so () would be a bad choice.  If NIL were just another symbol, that
would be a foolish choice.  So the NIL that's returned now must be NIL
in the boolean sense.

So, I guess what I'm saying is that you ought to explain your
objection here (or point to a message where you've explained it
before, since I'm sure you have).

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Kenny Tilton
Subject: Re: On conditionals
Date: 
Message-ID: <3BFC2BC7.BDD2CEF0@nyc.rr.com>
"Thomas F. Burdick" wrote:
>  I don't even see any good reason why NIL should
> be false. 

Understood, but in this case the proof is in the pudding for me. By
which I mean, programming with nil as false is so terrific it must be
Deeply Right.

isn't there a funny essay somewhere about the consequences of porting
something from Lisp to Scheme, specifically about the problem of having
to then differentiate between nil and false? I recall assoc figuring
prominently in the piece.

kenny
clinisys
From: Thomas F. Burdick
Subject: Re: On conditionals
Date: 
Message-ID: <xcvelmrvikm.fsf@conquest.OCF.Berkeley.EDU>
Kenny Tilton <·······@nyc.rr.com> writes:

> "Thomas F. Burdick" wrote:
> >  I don't even see any good reason why NIL should
> > be false. 
> 
> Understood, but in this case the proof is in the pudding for me. By
> which I mean, programming with nil as false is so terrific it must be
> Deeply Right.

But have you tried programming in a CL-like dialect where (), nil, and
boolean false were three different objects?  Otherwise, that would be
somewhat like saying that lexical scoping was a bad idea because you
had so much more fun in Maclisp or Interlisp than in Scheme.

> isn't there a funny essay somewhere about the consequences of porting
> something from Lisp to Scheme, specifically about the problem of having
> to then differentiate between nil and false? I recall assoc figuring
> prominently in the piece.

Oh boy, how I hate when code depends on the pun between false and ().
Bleah.  Would it really kill people to put a couple (not (null ..))s
here and there, and make their intentions more explicit?

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Kenny Tilton
Subject: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3BFC3F7F.E31CBAF0@nyc.rr.com>
"Thomas F. Burdick" wrote:
> Oh boy, how I hate when code depends on the pun between false and ().
> Bleah.  Would it really kill people to put a couple (not (null ..))s
> here and there, and make their intentions more explicit?

Omigod. You actually consider:

   (when (find long-sought-thing input-stuff)
      <stuff to do>)

hatefully inferior readability-wise to a double-negative? You can read
double-negatives?! Tell your programmers you just failed the Turing
Test.

Seriously, I think NIL as false is Deeply Correct. Consider FIND. Your
position is that (find x y) returns two possible values, x or nil. Too
literal. FIND either finds x or it does not.

kenny
clinisys
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcvd72bljpt.fsf@apocalypse.OCF.Berkeley.EDU>
Kenny Tilton <·······@nyc.rr.com> writes:

> "Thomas F. Burdick" wrote:
> > Oh boy, how I hate when code depends on the pun between false and ().
> > Bleah.  Would it really kill people to put a couple (not (null ..))s
> > here and there, and make their intentions more explicit?
> 
> Omigod. You actually consider:
> 
>    (when (find long-sought-thing input-stuff)
>       <stuff to do>)
> 
> hatefully inferior readability-wise to a double-negative? You can read
> double-negatives?! Tell your programmers you just failed the Turing
> Test.

But (not (null ...)) is only a double negative when you're punning on
false and ()!  NULL checks for end-of-list-ness.  NOT negates.  Do you
consider (not (zerop ...)) to be a double negative?  I certainly hope
you don't write (null (symbolp foo)) to negate the boolean value
returned by SYMBOLP.

But, yes, my first reaction to your code above is that FIND returns a
boolean.  Really, it returns a list.  So the body of your WHEN is
being run when FIND returns a non-empty list, not when it returns
true.  Imagine recasting it numerically:

  (when (not (zerop (count long-sought-thing input-stuff)))
     (do-stuff))

if that had been:

  (when (count long-sought-thing input-stuff)
     (do-stuff))

you would assume that COUNT was a predicate.

> Seriously, I think NIL as false is Deeply Correct. Consider FIND. Your
> position is that (find x y) returns two possible values, x or nil. Too
> literal. FIND either finds x or it does not.

No, my position is that there's a conceptual difference between the
empty list (), and the boolean false NIL.  And that it's kinda weird
that false is a symbol.

None of this causes me much of a headache, though, and it's usually a
difference of a half a second or less to figure out that someone meant
false, not ().

And, so there's no misunderstanding, I don't mean to rehash this in
any sort of Common-Lisp-is-broken-because... or The Next Standard
Should Do... sort of way.  I just don't think it's nutty to
distinguish NIL, (), and flase.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215382911849059@naggum.net>
* Thomas F. Burdick
| Do you consider (not (zerop ...)) to be a double negative?

  That depends on how you use it.  I prefer (/= 0 ...) to duoble predicates.

| But, yes, my first reaction to your code above is that FIND returns a
| boolean.  Really, it returns a list.

  But find _does_ return nil or the object you asked it to find.  It does
  _not_ return a list, because it _cannot_ return a cons unless you have
  asked it to find a cons, which is a statement about the specific call,
  not about the function in general.  (Functions like this that return nil
  or cons are member and assoc.)  The function position also returns nil or
  the position where it found something, not a cons, so its notion of true
  is simply "non-nil".

  I maintain that it would not make sense to make nil or () not be false
  without making every other object also not be true.  If punning on false
  is bad, punning on true is also bad.  If we have a pure boolean type, we
  would need to rethink this whole return value business and consider pure
  predicates, not just for things like null to see if a list is empty, but
  it would also be wrong to give it a non-list.  So this is not a question
  just of (not (null ...)), but of (and (listp ...) (not (null ...))),
  which is again what (consp ...) does more efficiently, so the whole (not
  (null ...)) thing is kind of moot.  It works today _because_ of the pun
  on true and false.  It would not make sense to use null on non-lists in a
  strict boolean-type universe, because boolean would not be the only type
  to be treated anal-retentively.

| So the body of your WHEN is being run when FIND returns a non-empty list,
| not when it returns true.

  I think you should look up what find does and returns, now...

| Imagine recasting it numerically:
| 
|   (when (not (zerop (count long-sought-thing input-stuff)))
|      (do-stuff))
| 
| if that had been:
| 
|   (when (count long-sought-thing input-stuff)
|      (do-stuff))
| 
| you would assume that COUNT was a predicate.

  But this carefully elides the context in which nil = () = false makes
  sense.  In a language where you return pointers or indices into vectors,
  0 = NULL = false makes sense.  In such a language, you could not have a
  function position that returned the position where it found something,
  because 0 would 

| No, my position is that there's a conceptual difference between the empty
| list (), and the boolean false NIL.  And that it's kinda weird that false
| is a symbol.

  Since there _is_ no "false" concept as such, but rather "nothing" vs
  "thing" that supports a _generalized false_, I think the conclusion only
  follows because you think the type boolean is defined differently than it
  is.  In fact, the boolean type is defined as the symbols t and nil.
  (Please look it up in the standard.)

| None of this causes me much of a headache, though, and it's usually a
| difference of a half a second or less to figure out that someone meant
| false, not ().

  I think this betrays a conceptual confusion.  If you realized that they
  are in fact exactly the same thing, you would not need to think about it,
  but since you think they are something they are not, it takes think time
  to undo the confusion.  It is much smarter to fix the confusion at its
  core and realize that you you cannot get what you want because what you
  want is not within the tradition that produced Common Lisp.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3BFC6AB7.4B7B99B9@nyc.rr.com>
"Thomas F. Burdick" wrote:
> 
> But (not (null ...)) is only a double negative when you're punning on
> false and ()!

Touche! But this confirms you are composed of logic gates.

>  Do you
> consider (not (zerop ...)) to be a double negative?

Zero is negative? :) Well I cannot understand even singly-negated tests.
The only time I use NOT is for:

 (if (not <test>)
     'no
     <50 lines of code>)


>  I certainly hope
> you don't write (null (symbolp foo)) to negate the boolean value
> returned by SYMBOLP.

If I have to choose between NULL and NOT I indeed use NOT against
predicates and NULL against existence, but this only happens because for
some reason I have for some reason been cornered into coding one or
another of those. But (not (null <test>)) not only obfuscates, it adds
two keywords where none were needed.

> No, my position is that there's a conceptual difference between the
> empty list (), and the boolean false NIL.

Buddha taught that in the beginning was the void, and the void became
nothing and something, and the something became the multitude. So
nothing, false, empty are all the same while true comes in many forms.

After we come to agreement on this let's go over to comp.lang.c and get
everyone agree on where to put {}s. :)

kenny
clinisys
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcv3d37pid0.fsf@conquest.OCF.Berkeley.EDU>
Kenny Tilton <·······@nyc.rr.com> writes:

> "Thomas F. Burdick" wrote:
> > 
> > But (not (null ...)) is only a double negative when you're punning on
> > false and ()!
> 
> Touche! But this confirms you are composed of logic gates.

Crud, I thought those were neurons in there.

 [...]
> If I have to choose between NULL and NOT I indeed use NOT against
> predicates and NULL against existence, but this only happens because for
> some reason I have for some reason been cornered into coding one or
> another of those. But (not (null <test>)) not only obfuscates, it adds
> two keywords where none were needed.

Shoot, I don't think I ever use find (I couldn't find any instances in
a big chunk of code -- plenty of "member"s, though), and I was
mistaken about what it does (I thought it returned a list of the
matching items, oops).  Which makes this exchange heavy in the
talking-past-eachother area.  Absolutely, (not (null (predicate))) is
confusing.
(not (null (returns-a-list))) is what I meant to be talking about.  Of
course, I'm more likeley to check based on type, or to put (null ...)
higher in the cond, letting non-empty lists fall through for more
testing.

> > No, my position is that there's a conceptual difference between the
> > empty list (), and the boolean false NIL.
> 
> Buddha taught that in the beginning was the void, and the void became
> nothing and something, and the something became the multitude. So
> nothing, false, empty are all the same while true comes in many forms.

Yeah, but he also taught that after I'm dead, I'm not gone.

> After we come to agreement on this let's go over to comp.lang.c and get
> everyone agree on where to put {}s. :)

They *still* haven't gotten that figured out?  Maybe they could use
some help :-)

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3BFC92C8.FE1BCD84@nyc.rr.com>
OK, let's finish off this dead horse...

I agree '() being false being nil is confusing at first. I just
remembered what it was like when I was first learning Lisp. My feeling
was, OK, they're making this sh*t up as they go along. But now it feels
so natural I had no idea what you were going on about--until I
remembered my early experience.

Which takes me back to my pudding proof. If it was Truly Confused (like
some things I have worked with) it would never feel natural. But it
feels natural, so the problem up front must have been with me.

Scheme worked from first principles when they "improved" on this. That
is always dangerous. We are not as smart as we think. Who says we have
the first principles right? One of my design rules says good design
changes lead to less code; if I find myself adding code such as (not
(null ...)) all over the place I back out the change. Schemers should
have done the same when they saw the consequences of their change.

I believe it was David St. Hubbens (in collaboration with Nigel) who
said, It's a fine line between clever and stupid.

kenny
clinisys
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcvu1vnni2j.fsf@conquest.OCF.Berkeley.EDU>
Kenny Tilton <·······@nyc.rr.com> writes:

> OK, let's finish off this dead horse...

(Oh don't tempt me, a friend and I used to have this joke about dead
horses.  See, there's this funny thing, where you keep beating them.
And, yeah, you've heard this before, but it's really funny.  Anyways,
dead horse, yeah.  So, I was beating it ... [you get the idea, I hope].)

> I agree '() being false being nil is confusing at first. I just
> remembered what it was like when I was first learning Lisp. My feeling
> was, OK, they're making this sh*t up as they go along. But now it feels
> so natural I had no idea what you were going on about--until I
> remembered my early experience.
> 
> Which takes me back to my pudding proof. If it was Truly Confused (like
> some things I have worked with) it would never feel natural. But it
> feels natural, so the problem up front must have been with me.

I don't know that the problem is the inexperienced user.  It certainly
feels natural to me anymore (despite the fact that I have
philosophical issues with it), but then, so do the wacky rules of
English and French grammar.  And some of the "unintuitive" bits of
evolution science (I remember when they seemed weird, but it takes
effort).  But our current conception of evolution could very well be
off, and I don't think it takes a genius to figure out that English is
a crazy (if practical) language.

Oy, I really didn't mean to draw this out into a long thread.  I
*really* just wanted to refute the idea that it was nuts to separate
NIL and false.  For all the arguments in that direction, the obvious
usability of Common Lisp means that it's also reasonable to conflate
them, despite any conceptual messiness that might (or might not)
entail.  I kept responding because I felt like I needed to clarify
myself.  And then, here we are with a long thread that should've been
3 messages long.  (sigh).  So, this is my last post to this thread,
and not just because I'm about to be away from home for a few days
:-).  It should have died already, and I think it's my fault it
hasn't.  On that note, here are some nice words from R. Kelly, having
nothing to do with Lisp, (), NIL, false, nor Scheme:

"I don't see nothing wrong
 [...]
this is going on 'til the early morn'
and my word is bond."

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfw8zcy507w.fsf@shell01.TheWorld.com>
···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) writes:

> It certainly feels natural to me anymore (despite the fact that I
> have philosophical issues with it), but then, so do the wacky rules
> of English and French grammar.

[You don't have to take this personally, Thomas.  I'm starting from 
 your remark here because it was a good starting point, but the comments
 are directed generally to anyone that "fits the bill"...]

But this is EXACTLY the point people are trying to make.

The Scheme community (and, I would say, the FP community in general)
wants to DEFINE what is natural and easy by a simplicity metric they
pulled out of a hat, as if the very meaning of natural/easy is
uniquely determined/predicted by that simplicity metric.  It is not.
That's a possible theory of simplicity, but it is (a) not proven to in
fact make things simpler for most people and (b) not proven to be the
only way to make things simpler for most people.

The Scheme community then works to minimize the number of premises
they work from, as if minimizing this one axis in what is obviously a
multivariate system will yield a consequent minimization of the other
axes by magic.  I don't buy that.  First, I see language size and
isolated sentence size as inversely correlated.  The bigger the
language, the less you have to say.  THat is, a language that has has
all 64 crayola crayon colors as primitive concepts is at a marked
advantage for describing a sunset over one that has only the primary
colors plus the modifier words "saturated", "bright", "dark" and
adverbials like "not" and "very".  So it may please some teacher of
this Esperanto-like "simple" language to to know he "empowered" people
generally to describe ANYTHING with his tools, but it won't
necessarily please the reader of a fine novel to see the sunset
described as a "very, very, light, unsaturated mix of blue and red" if
what is meant is "lavender".  The reason "lavender" works, even though
it takes a long time to learn all the subtle color names, is that your
brain wetware learns to make a primitive connection from this word to
this color and doesn't have to waste compute time simulating things.
Moreover, it can be compared in more "satisfying" ways to other colors
like "orchid" than can "very, very, light ..." be compared to just
"very light..."  Sure, you can make all the claims you want about the
extra word "very" being missing giving the same sense, but that still
requires you to remember the *input* string and deal with it as a
formal algebraic string because the human brain is not a precise
enough processor to actually carry the consequence of such thought
exercises primitively.  I know my girlfriend often orders a medium
coffee extra extra extra light from Dunkin Donuts but I've seen them
sometimes give her a medium coffee extra extra light, which both
suggests that people receiving such data are bad at holding even that
long a string in their head and that she's unable to hold the precise
notion of that concept in her head.

Now, second, the Scheme community has another very unwarranted premise
underlying a great deal of its teaching, and it overflows sometimes
into design: that's that if they can find a simpler way to express
things (using their simplicity metric: smaller language) that this
will autmatically lead something to be easier to learn.  This makes
unstated assumptions about how people think and how people learn.  I
claim, without enumerated proof here, but with a belief that at least
I could dredge up proof if I had to because psychologists do research
these things all the time, that the human brain is not like an Intel
box, and that people do not operate on a RISC instruction set.  I
think people have a highly parallel associative mechanism capable of
efficiently managing an enormous amount of special cases at the same
time.  All naturally-designed human languages that I know of, not
counting the ones that were designed by professional logicians or
computer people, have tons of special cases, have context, etc.  Of
course, human languages are all very different, each with their own
idiosyncracies.  But what this tells you is that it's ok to have some
variation here.  Humans will cope.

I think the fact is that the reason to keep programming languages
simple is not for the sake of humans, but for the sake of code.  So
yes, for the sake of code, not making the language too difficult will
make programming easier.  But on that we have a 25-or-so year history
during which both Scheme and CL have existed, and in no cases have I
ever seen or heard of someone tearing out their hair and leaving the
CL community saying "I just can't build complex programs because this
NOT/NULL [or false/empty-list] thing is making it too hard to write
metaprograms".  It just doesn't happen.  So no one ever points to that
as the reason for splitting false/empty-list.  They point instead into
the murky depths of the human brain, citing simplicity without
defining their simplicity metric, citing how hard it is for students
to learn (which it is, in the abstract, but mostly because students
are often ill-trained to learn).  I sometimes would go so far as to
think some students of Scheme are indoctrinated by some teachers to
actually reject, almost as a political action, the possibility of
receiving certain kinds of learning because they recognize it as not
simple enough.  Yet they have somehow managed to recognize and adopt
this whole anti-complexity complexity when it would be simpler to just
learn things than to apply political philosophy to everything you
learn.  The only other place I've ever seen that kind of resistance is
in recent converts to this or that church, who are never sure if they
should try to directly understand a truth you're trying to offer them
because they're not sure it's offered to them in a form that it would
be good for them to receive it in.

But to me, the issue of what makes a language easy/hard to use is the
dissonance between the mental representation of the user and the
manifest structure of the program.  I have some theories about that,
but I acknowledge this as a hard problem.  I'm not trying to argue CL
is an utterly simple language to learn and use.  But people do often
claim that Scheme is simple to learn and use, and also that it is
simpler to learn and use than CL, and I'm arguing against accepting
such claims without better proof.  If someone doesn't bring either
serious case studies or serious psychological evidence of mental
models into play in the discussion, I think it's worth questioning all
these unstated simplicity metrics that are advanced instead.

On learning and understanding, I think this: Years ago, I taught
myself Portuguese in anticipation of a couple of weeks vacation I was
going to spend in Brasil, it didn't occur to me that it was going to
be pronounced differently than Spanish.  When I got to Rio, I found
some people who could understand me and some who couldn't.  It wasn't
smart people who understood me and stupid people who didn't.  It
crossed those lines.  The line I eventually drew was that people who
wanted to understand me (i.e., those who stubbornly resisted
entertaining the implausible notion that what was coming from my mouth
might not be "an attempt at language") had no trouble understanding
me.  But those who didn't want to understand me, or didn't mind not
understanding me, looked at me with blank stares.  I'm convinced those
people actually had allowed themselves to think "perhaps this isn't
speech but just some kind of useless babble", and the believe that
this "simpler" answer could be true allowed them to rest confident
that not understanding me was the simplest answer to their
conversational dilemma.  I really think the same of Lisp.  Some people
see the NOT/NULL thing or the false/empty-list thing and decide "it
probably means the langauge is incapable of expressing anything
plainly".  And voila, they find proof of their claim in the fact that
they cannot express themselves.  Or else they decide that it's just an
artifact of the language that can/must be worked with, and, wonder of
wonders, it never becomes a problem.  But the dividing line is not
that language feature.  

Languages CAN accomodate ambiguity. (A huge percentage of all words in
all languages have multiple definitions, based on context.)  Languages
cannot accomodate a closed mind.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-9A9045.05423323112001@news.paradise.net.nz>
In article <···············@shell01.TheWorld.com>, Kent M Pitman 
<······@world.std.com> wrote:

> we have a 25-or-so year history
> during which both Scheme and CL have existed, and in no cases have I
> ever seen or heard of someone tearing out their hair and leaving the
> CL community saying "I just can't build complex programs because this
> NOT/NULL [or false/empty-list] thing is making it too hard to write
> metaprograms".  It just doesn't happen.  So no one ever points to that
> as the reason for splitting false/empty-list.  They point instead into
> the murky depths of the human brain, citing simplicity without
> defining their simplicity metric

Here's what I don't get about CL confusing false and the empty list:  
suppose you have a function (foo name) that returns a list of all the 
classes being taken by a student.  If the function returns NIL, does 
that mean that the student is taking no classes at the moment, or does 
it mean that the student doesn't exist?

It seems to me that *every* datatype deserves to potentially have a 
"don't know" or "doesn't exist" value.  Like NULL in SQL.  An integer 
field in a database can allow NULL, or can be declared to be NOT NULL 
and this is an important distinction.  In any complex program some code 
needs to be written to cope with NULL values, and some code wants to 
assume that there is always valid data.

It's bad to use a value of zero in an integer variable to mean NULL.  
It's bad to use a value of -1 in an integer variable to mean NULL.  It's 
also bad, I think, to have a null pointer value in every pointer data 
type.  How often do C programs fail because some function gets passed a 
null pointer that didn't expect it?

It seems to me that using an empty list to represent NULL is just as bad.

-- Bruce
From: Dr. Edmund Weitz
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <m3snb6bv85.fsf@bird.agharta.de>
Bruce Hoult <·····@hoult.org> writes:

> Here's what I don't get about CL confusing false and the empty list:
> suppose you have a function (foo name) that returns a list of all
> the classes being taken by a student.  If the function returns NIL,
> does that mean that the student is taking no classes at the moment,
> or does it mean that the student doesn't exist?

That's what multiple values are for in CL, see the CLHS for GETHASH
for an example.

Edi
From: Rahul Jain
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87d72ahxqk.fsf@photino.sid.rice.edu>
···@agharta.de (Dr. Edmund Weitz) writes:

> That's what multiple values are for in CL, see the CLHS for GETHASH
> for an example.

Or conditions, if that's the way that's most natural to handle it in
your application. (Maybe seeing an unknown student means that either
the input is bogus or there's an inconsistency in the database or
something)

-- 
-> -/-                       - Rahul Jain -                       -\- <-
-> -\- http://linux.rice.edu/~rahul -=- ·················@usa.net -/- <-
-> -/- "I never could get the hang of Thursdays." - HHGTTG by DNA -\- <-
|--|--------|--------------|----|-------------|------|---------|-----|-|
   Version 11.423.999.220020101.23.50110101.042
   (c)1996-2000, All rights reserved. Disclaimer available upon request.
From: Frode Vatvedt Fjeld
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <2hlmgy218l.fsf@dslab7.cs.uit.no>
Bruce Hoult <·····@hoult.org> writes:

> Here's what I don't get about CL confusing false and the empty list:
> suppose you have a function (foo name) that returns a list of all
> the classes being taken by a student.  If the function returns NIL,
> does that mean that the student is taking no classes at the moment,
> or does it mean that the student doesn't exist?

To me that would be (at least in principle) a poorly specified
function that performs two unrelated tasks: Checking whether a student
exists and listing a student's current classes. Those should be
separate functions, and calling the latter function on an unknown
student would be an error (exceptional situation). If for some reason
those two tasks must be smashed into a single function, good style
would be to return two values from that function. It would also be
possible to return a designated symbol like :no-such-student, although
I'd consider that an inferior option, stylewise.

> It seems to me that *every* datatype deserves to potentially have a
> "don't know" or "doesn't exist" value.

I disagree.

-- 
Frode Vatvedt Fjeld
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-C50EA9.06254123112001@news.paradise.net.nz>
In article <··············@dslab7.cs.uit.no>, Frode Vatvedt Fjeld 
<······@acm.org> wrote:

> Bruce Hoult <·····@hoult.org> writes:
> 
> > Here's what I don't get about CL confusing false and the empty list:
> > suppose you have a function (foo name) that returns a list of all
> > the classes being taken by a student.  If the function returns NIL,
> > does that mean that the student is taking no classes at the moment,
> > or does it mean that the student doesn't exist?
> 
> To me that would be (at least in principle) a poorly specified
> function that performs two unrelated tasks: Checking whether a student
> exists and listing a student's current classes. Those should be
> separate functions, and calling the latter function on an unknown
> student would be an error (exceptional situation).

Quite possibly, though an exception is a pretty heavy-weight mechanism.  
You might also want to delay the exception until the client code 
actually tries to use the value inappropriately.


> If for some reason those two tasks must be smashed into a single
> function, good style would be to return two values from that
> function.

That also seems pretty heavy-weight given that you're already taking a 
hit for using a dynamically-typed language in which every value has a 
general enough representation to be a number, string, symbol or anything 
else.


> It would also be possible to return a designated symbol like
> :no-such-student, although I'd consider that an inferior option,
> stylewise.

I think that's a reasonable thing to do, and also that "false" is a 
pretty good designated symbol to use.

 
> > It seems to me that *every* datatype deserves to potentially have a
> > "don't know" or "doesn't exist" value.
> 
> I disagree.

So you want to have pairs of variables nearly everywhere, with one being 
a boolean saying whether or not the other one is valid?  And slots to be 
in pairs?  And functions to return two values?

Seems very strange when you only need one bit to represent that second 
value, and the language you are using has *already* made provision to 
incorporate that sort of information in every value.  Every value, that 
is, except for the empty list.

-- Bruce
From: Frode Vatvedt Fjeld
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <2h1yiqn1fr.fsf@dslab7.cs.uit.no>
Bruce Hoult <·····@hoult.org> writes:

>> To me that would be (at least in principle) a poorly specified
>> function that performs two unrelated tasks: Checking whether a student
>> exists and listing a student's current classes. Those should be
>> separate functions, and calling the latter function on an unknown
>> student would be an error (exceptional situation).
>
> Quite possibly, though an exception is a pretty heavy-weight
> mechanism.  You might also want to delay the exception until the
> client code actually tries to use the value inappropriately.

An error is sort of a heavy-weight thing regardless of the costs
associated with signaling conditions. If signaling an error is the
right thing to do, then not doing so because it is or might be
"heavy-weight" is to me a rather absurd notion.

>> If for some reason those two tasks must be smashed into a single
>> function, good style would be to return two values from that
>> function.
>
> That also seems pretty heavy-weight given that you're already taking
> a hit for using a dynamically-typed language in which every value
> has a general enough representation to be a number, string, symbol
> or anything else.

I don't consider returning multiple values to be prohibitively
expensive except possibly in situations where extreme optimization is
required, in which case the rules of "good style" change
entirely. What good is having a rich language if you can't use it?

> So you want to have pairs of variables nearly everywhere, with one
> being a boolean saying whether or not the other one is valid?  And
> slots to be in pairs?  And functions to return two values?

I think Common Lisp is excellent evidence that this works out very
well in practice.

-- 
Frode Vatvedt Fjeld
From: Pierre R. Mai
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87r8qq8djk.fsf@orion.bln.pmsf.de>
Bruce Hoult <·····@hoult.org> writes:

> In article <··············@dslab7.cs.uit.no>, Frode Vatvedt Fjeld 
> <······@acm.org> wrote:
> 
> > Bruce Hoult <·····@hoult.org> writes:
> > 
> > > Here's what I don't get about CL confusing false and the empty list:
> > > suppose you have a function (foo name) that returns a list of all
> > > the classes being taken by a student.  If the function returns NIL,
> > > does that mean that the student is taking no classes at the moment,
> > > or does it mean that the student doesn't exist?
> > 
> > To me that would be (at least in principle) a poorly specified
> > function that performs two unrelated tasks: Checking whether a student
> > exists and listing a student's current classes. Those should be
> > separate functions, and calling the latter function on an unknown
> > student would be an error (exceptional situation).
> 
> Quite possibly, though an exception is a pretty heavy-weight mechanism.  
> You might also want to delay the exception until the client code 
> actually tries to use the value inappropriately.

Why would that be an appropriate thing to do?  This seems like the C
philosophy of doing error-checking:  "Never report errors at the place
where they actually occurred (calling a function that is specified to
take the name of an existing student with something else), but delay
it as long as necessary to destroy all relevant context; make it
maximally inconvenient to check for error situations; and above all
else, rather crash maximally fast, or produce wrong results, than
throwing away one instruction on detecting errors".

If that is your attitude about error checking, than I don't think that
(eq 'nil '()) is something you need to fret about, for a looong time.

Furthermore why care about the cost of exceptions in such a situation?
Unless your program is buggy as hell (i.e. calls foo with non-student
names all of the time, in-spite of foo's specification), that is.  If
it is important to differentiate between non-students and students
with no courses, _you don't call foo with an unchecked name_.  Period.

You write instead:

(defun bar (some-random-name)
  (cond
   ((student-p name)
    (let ((courses (foo name)))
      ;; Do something silly here...
      ))
   (t
    ;; Do something differently silly here...
    )))

The only thing that a non-nil "NULL" value would give you here, is the
ability to write instead

(defun bar (some-random-name)
  (let ((courses-or-student-status (foo name)))
    (cond
     ((not courses-or-student-status)
      ;; Do something differently silly here...
      )
     (t
      ;; Do something silly with courses-or-student-status here, but
      ;; we now know it actually is a list, not some overloaded 
      ;; other return value-type...
      ))))

And that's the point where I'm thanking the powers that were, that we
don't see this kind of code all over the place.  FOO should never have
been specified like this in the first place, if there really is a
difference between non-students and students with no courses.  What
would be a descriptive name for foo?  STUDENT-COURSES-AND-STUDENT-P?

> > If for some reason those two tasks must be smashed into a single
> > function, good style would be to return two values from that
> > function.
> 
> That also seems pretty heavy-weight given that you're already taking a 
> hit for using a dynamically-typed language in which every value has a 
> general enough representation to be a number, string, symbol or anything 
> else.

Multiple values are cheap in serious implementations.  If I were prone
to armchair musing, I might conjecture that distinguishing between
'NIL and '() would have higher costs in terms of register and cache
pressure (as well as tag "pressure"), than pervasive usage of
two-value functions.

> > It would also be possible to return a designated symbol like
> > :no-such-student, although I'd consider that an inferior option,
> > stylewise.
> 
> I think that's a reasonable thing to do, and also that "false" is a 
> pretty good designated symbol to use.

Well you can already do this.  You just have to write

(eq courses-or-student-status #f)

instead of 

(not courses-or-student-status)

Not that I would consider code that did this to be well written code.
It actively encourages the same kind of lossage you get in C, where we
have all of those "failure" indicating values, that you have to
manually check, and if you don't (who does), work very nicely to
increase the time between error occurrance and error detection.

Regardless of any (eq 'NIL '()) issue, I can't see any justifiable
reason (senseless obsession about speed isn't one), for a function
student-courses that returns anything but a list (or other collection
datastructure).  Either you define non-students names to be valid
arguments to that function, then you should just return the empty list
(collection, whatever) for non-students, or you say "student-courses
is actually not defined for non-students", in which case you signal an
error when called with a non-student name.

I'm even critical of a multiple-value version that _additionally_
indicates whether we're really talking about a student.  But in cases
where this is justified, that additional value doesn't say "the
primary value is valid or not".  The primary value is always valid,
and has the normal meaning.  The secondary value just _adds_
additional information.  Doing anything else just opens the door for
undetected error situations.  We could then just as well be doing
errno in Common Lisp...

Doing anything else is just plain bad code in my book.

> > > It seems to me that *every* datatype deserves to potentially have a
> > > "don't know" or "doesn't exist" value.
> > 
> > I disagree.
> 
> So you want to have pairs of variables nearly everywhere, with one being 
> a boolean saying whether or not the other one is valid?  And slots to be 
> in pairs?  And functions to return two values?

I'm beginning to wonder if you have actually ever looked at real
Common Lisp code.  How do you come up with such completely foolish
ideas?  No one is suggesting such foolishness, because nothing of the
sort is necessary.  If your code makes that kind of nonsense
necessary, by conflating validity information and data content in one
place all over the place, then it is bad code, for reasons that are
completely unrelated to the topic under discussion.

Regs, Pierre.

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: ·······@Yahoo.COm
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <ffdf35bb.0112101922.411a7052@posting.google.com>
"Pierre R. Mai" <····@acm.org> wrote in message news:<··············@orion.bln.pmsf.de>...
> > Quite possibly, though an exception is a pretty heavy-weight mechanism.
> > You might also want to delay the exception until the client code
> > actually tries to use the value inappropriately.
>
> Why would that be an appropriate thing to do?  This seems like the C
> philosophy of doing error-checking:  "Never report errors at the place
> where they actually occurred (calling a function that is specified to
> take the name of an existing student with something else), but delay
> it as long as necessary to destroy all relevant context; make it
> maximally inconvenient to check for error situations; and above all
> else, rather crash maximally fast, or produce wrong results, than
> throwing away one instruction on detecting errors".

I agree, and repeated your excellent rebuke of that idea for emphasis.
In general, an exceptional condition should be detected as soon as
possible and immediately diagnosed as to whether the rest of the program
can meaningfully continue under such circumstances, and if not then
a nice clean error should be reported somehow, and if proceedable then
the exception should be cleanly noted and handled specically in the
rest of the program. For example if ten people try to drop courses,
and only nine are legitimate students, the other being a typo, or a
prankster, it should report the one non-student but proceed to handle
the other nine normally.

> Furthermore why care about the cost of exceptions in such a situation?
> Unless your program is buggy as hell (i.e. calls foo with non-student
> names all of the time, in-spite of foo's specification), that is.  If
> it is important to differentiate between non-students and students
> with no courses, _you don't call foo with an unchecked name_.  Period.

I totally disagree. Think *distributed/shared*database*. Think concurrent
processes over a localnet. Think one part of Registrar's office handling
adding and deleting students and fixing typos in admission records, while
another part handles less drastic actions such as adding/removing courses,
and users completely outside the Registrar's office can do non-modifying
queries such as just listing the current courses in a report to the student's
academic supervisor. The application we are discussing is clearly of this
kind where a database record might disappear or be change out from under
a running program that has already checked that it exists, so EVERY
database query must allow for the possibility the desired record ceased
to exist since the last time we checked just a few microseconds ago.
Every time you make a call to the database-query utility, the utility must
check *again* to be sure the desired record still exists. It's not
acceptable to lock the whole database, or even lock one record, just
because some graduate student is debugging a utility to improve generation
of reports of student classes, while the Registrar is desperately trying
to delete a misspelled student record so that billing (due in less than
one hour) can run correctly. Better have the unimportant program merely
fail in a strange way (record which existed when we asked if it existed,
and again when we got student's name, and again when we got list of courses,
and again when we looked up the first three out of five courses for
details, suddenly ceased to exist) which the programmer can then check and
see indeed somebody has finally fixed that spelling error so we have to
re-start the debug run to proceed from this point.

> You write instead:
>
> (defun bar (some-random-name)
>   (cond
>    ((student-p name)
;;Registrar's program deleted that student at this inopportune moment.
>     (let ((courses (foo name)))
;;This program crashes and burns somewhere around now...
>       ;; Do something silly here...
>       ))
>    (t
>     ;; Do something differently silly here...
>     )))
>
> The only thing that a non-nil "NULL" value would give you here, is the
> ability to write instead
>
> (defun bar (some-random-name)
;;If registrar deleted record about here, then ...
>   (let ((courses-or-student-status (foo name)))
>     (cond
;;... program will get a nice clean detection of that fact here ...
>      ((not courses-or-student-status)
>       ;; Do something differently silly here...
;;... and a nice clean fail-soft action there was not at all silly.
>       )
>      (t
>       ;; Do something silly with courses-or-student-status here, but
>       ;; we now know it actually is a list, not some overloaded
>       ;; other return value-type...
;;And if the Registrar deletes the record anywhere inside that code,
;; then there's yet another chance for fail-soft inside there if we
;; check for record-not-exist every time we call the db-query utility.
>       ))))
>
> And that's the point where I'm thanking the powers that were, that we
> don't see this kind of code all over the place.  FOO should never have
> been specified like this in the first place, if there really is a
> difference between non-students and students with no courses.  What
> would be a descriptive name for foo?  STUDENT-COURSES-AND-STUDENT-P?

There most definitely is a difference. If it's a student not taking
any courses, the student can always take one more course, just like
Alice and the teaparty, whereas if not a student then taking a course
is forbidden. Very important difference to any college!

We don't need a weird name like that. (READ Stream NIL EOFvalue)
normally just reads from a stream, but if it can't read because EOF
has already been reached then it returns the EOFvalue. Likewise,
(OPEN  ... :IF-DOES-NOT-EXIST NIL) normally just opens the file,
but silently returns NIL if there's no such file to open, and we just
call that function OPEN rather than a weird name. Perhaps the database
query utility could likewise have keyword arguments for that to do
under various unusual situations (database doesn't exist, record doesn't
exist because there's no such studeht, record exists but forwards
to another record because a typo has been fixed), with defaults perhaps
being to signal an error in each unusual case where normal function
can't proceed. (STUDENT-COURSE &keyword :IF-SERVER-DOES-NOT-RESPOND
:IF-DATABASE-DOES-NOT-EXIST :IF-DATABASE-LOCKED :IF-RECORD-DOES-NOT-EXIST
:IF-RECORD-FORWARDS :IF-RECORD-LOCKED :IF-MACHINE-ERROR)

> > > It would also be possible to return a designated symbol like
> > > :no-such-student, although I'd consider that an inferior option,
> > > stylewise.
> >
> > I think that's a reasonable thing to do, and also that "false" is a
> > pretty good designated symbol to use.
>
> Well you can already do this.  You just have to write
>
> (eq courses-or-student-status #f)

Better would be to define a predicate for testing that status, so
at compile/build time you can get told if you mis-typed it so are trying
to call a function that isn't in the build rather than a runtime strangness
that the upper-case F being passed back by the utility somehow is never
caught by this one place in the program even though it's caught everywhere
else. (if (db-result-valid-p courses) somethingUsual somethingElse)
This is especially useful if there are more than one kind of failure,
such as record temporarily locked vs. record doesn't exist at all.
The predicate can catch all those various exceptional conditions with
one TRUE result, or NIL result for a normal db return, then in the case
of exceptional condition somebody else can diagnose what to do in each
of the various cases.
(defun db-result-valid-p (dbresult)
  (cond ((listp dbresult) t)
        ((member dbresult '(:locked :missing :crash)) nil)
        (t (error "Unexpected return value from db query ~S" dbresult))))

> instead of
>
> (not courses-or-student-status)

Even in that case I might like to encapsulate the conventions in use:
(defun db-result-valid-p (dbresult)
  (listp dbresult))
(defun db-result-record-numer (dbresult)
  (car dbresult))
(defun db-result-course-list (dbresult)
  (cdr dbresult))
;;Return value NIL means no such record or other problem accessing record,
;; otherwise return value is (recordNumber . listOfCourses)
(defun db-get-course-list (studentName)
  ... (return nil) ... (return nil) ... (return nil) ...
  ... (return (cons recnum courses)) ...)

> Not that I would consider code that did this to be well written code.
> It actively encourages the same kind of lossage you get in C, where we
> have all of those "failure" indicating values, that you have to
> manually check, and if you don't (who does), work very nicely to
> increase the time between error occurrance and error detection.

Good point. My solution with keyword arguments that specify if anything
other than signalling an error is to be done in case of trouble
would seem to be best. If the progammer is lazy, he/she gets a nice
clean error signaled from inside the database query utility, otherwise
presumably the programmer matched unusual return values specified by
those keyword arguments against code to check for those particular
return values. The specification of the keyword arguments in the call
are immediately before the place where the returned result is checked
for unusual cases, so it's pretty difficult to overlook a mismatch
where the keywords are supplied but no check for unusual return value
is done at all or explicit check for cases isn't same as possible cases
specified by keywords.

> Regardless of any (eq 'NIL '()) issue, I can't see any justifiable
> reason (senseless obsession about speed isn't one), for a function
> student-courses that returns anything but a list (or other collection
> datastructure).

See discussion of concurrent processes on local net accessing shared DB above.

> I'm even critical of a multiple-value version that _additionally_
> indicates whether we're really talking about a student.  But in cases
> where this is justified, that additional value doesn't say "the
> primary value is valid or not".  The primary value is always valid,
> and has the normal meaning.

Presumably the program leading into this db query will assure that
the data is syntactically valid, such as student's name must be
a string, or a list of four strings (first last middle Mr/Mrs/Ms),
but it might not be semantically valid (name of current student)
even if it was a moment ago so we must check for that every time.
From: Pierre R. Mai
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87g06hsc21.fsf@orion.bln.pmsf.de>
·······@Yahoo.COm writes:

> > Furthermore why care about the cost of exceptions in such a situation?
> > Unless your program is buggy as hell (i.e. calls foo with non-student
> > names all of the time, in-spite of foo's specification), that is.  If
> > it is important to differentiate between non-students and students
> > with no courses, _you don't call foo with an unchecked name_.  Period.
> 
> I totally disagree. Think *distributed/shared*database*. Think concurrent

The moment I think that, I also think competent programmers, which
know about transaction processing, etc.  Cramming lots of
functionality into functions in the mistaken belief that this will
solve such problems is totally silly.

> academic supervisor. The application we are discussing is clearly of this
> kind where a database record might disappear or be change out from under
> a running program that has already checked that it exists, so EVERY
> database query must allow for the possibility the desired record ceased
> to exist since the last time we checked just a few microseconds ago.

No!  You want ACID transactions.

> Every time you make a call to the database-query utility, the utility must
> check *again* to be sure the desired record still exists. It's not
> acceptable to lock the whole database, or even lock one record, just
> because some graduate student is debugging a utility to improve generation
> of reports of student classes, while the Registrar is desperately trying
> to delete a misspelled student record so that billing (due in less than
> one hour) can run correctly. Better have the unimportant program merely

Anyone who debugs programs on a live production database deserves
whatever they get.  Anyone who lets graduate students near his
production databases deserves it doubly so.

If you need a plain old RDBMS, buy one, don't try to fake one using
"pseudo-atomic" function calls.  Or if you really have to reinvent the
wheel, then do it properly, and provide a transaction processing
facility.  Don't just try to dodge issues like read/read consistency,
read/write consistency, ...

> There most definitely is a difference. If it's a student not taking
> any courses, the student can always take one more course, just like
> Alice and the teaparty, whereas if not a student then taking a course
> is forbidden. Very important difference to any college!

And that's why it is a bad idea cramming them into the same function.
You want

(with-transaction (:isolation-level :repeatable-read :read-only-p t)
  (unless (student-p name)
    (error "~A is not an active student"))
  (format T "Report on courses taken by ~A (Valid on: ~A):~2%"
            name (current-date-string))
  (dolist (course (student-courses name))
    (format T "~7,'0D ~A~%" (course-id course) (course-name course))))

[ This ignores the problem that you wouldn't use a persons name as a
  primary key ]

> We don't need a weird name like that. (READ Stream NIL EOFvalue)
> normally just reads from a stream, but if it can't read because EOF
> has already been reached then it returns the EOFvalue. Likewise,

That is because reaching EOF on a stream can be part of normal
operation (every file is finite).  Trying to get courses of
non-students just isn't part of normal operations, it is a clear
indication that something is amiss.

> Presumably the program leading into this db query will assure that
> the data is syntactically valid, such as student's name must be
> a string, or a list of four strings (first last middle Mr/Mrs/Ms),
> but it might not be semantically valid (name of current student)
> even if it was a moment ago so we must check for that every time.

Checking things every time not only doesn't solve your consistency
problems, it will also be horrendously slow in distributed systems.

Regs, Pierre.

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: ·······@Yahoo.Com
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <ffdf399b.0112101758.39ece63a@posting.google.com>
Frode Vatvedt Fjeld <······@acm.org> wrote in message news:<··············@dslab7.cs.uit.no>...
> To me that would be (at least in principle) a poorly specified
> function that performs two unrelated tasks: Checking whether a student
> exists and listing a student's current classes. Those should be
> separate functions, and calling the latter function on an unknown
> student would be an error (exceptional situation).

No no. Typically you don't want to have to shut down the whole University
every time this program is run, to prevent somebody else from running
a database update that installed a new student or removed an old student
or corrected a mis-typed name by removing the mistaken student while
adding the correctly-spelled named student. Scenerio:
(1) Your program asks does Mary Janf exist? Gets back YES.
(2) Somebody else corrects Mary Janf to be Mary Jane.
(3) Your program asks classes Mary Janf is taking, gets an error,
which is reported as a program bug.
So you want check-if-student-still-exists and get-class-list to be
sealed inside a single function call, so if you call first you get back
Mary Janf is taking these classes whereas if you call later you get nice
clean Mary Janf is not a student any more.

> If for some reason
> those two tasks must be smashed into a single function, good style
> would be to return two values from that function. It would also be
> possible to return a designated symbol like :no-such-student, although
> I'd consider that an inferior option, stylewise.

It's a pain to pass multiple values more than one level up in a program,
so if you're going to pass around these two facts you should either
use the exceptional value or make a list (or dotted pair) of two elements
or use some other way to keep the two results together on a single object.
However it would be reasonable for the database-lookup utility to return two
values, then the application program to encapsulate them into a list or
other single-object representation for passing around within the application.

> > It seems to me that *every* datatype deserves to potentially have a
> > "don't know" or "doesn't exist" value.
> I disagree.

The point is moot since you can always use a general (undeclared)
data type which can be any LISP data type whatsoever at any time, so
in particular you can have one data type for valid results and another
datatype for "don't know" or "no such", and there's not a lot of overhead
in checking which of those two datatypes a return result is before
proceeding with the rest of processing the return result.
(let ((res (student-classes name)))
  (if (success res) (print-schedule name res) (throw 'dbfail 'no-student)))
where success is a predicate that checks whether the returned result datatype
was valid or nosuch according to whatever your convention is, or
alternately with multiple returned values you would do:
(multiple-value-bind (existp classes) (student-classes name)
  (if existp (print-schedule name classes) (throw 'dbfail 'no-student)))
Caveat, I haven't tested either of those code snippits, so beware of typos.
From: Ola Rinta-Koski
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <x57kru84vx.fsf@arenal.cyberell.com>
·······@Yahoo.Com writes:
> (1) Your program asks does Mary Janf exist? Gets back YES.
> (2) Somebody else corrects Mary Janf to be Mary Jane.
> (3) Your program asks classes Mary Janf is taking, gets an error,
> which is reported as a program bug.

  The above behaviour would not be acceptable from a real-life
  application, hence none (that I know of) work that way. The way this
  would work is
  1) Your program asks: "Does Mary Janf exist?" Gets back YES and Mary
     Janf's student ID number XXX.
  2) As above.
  3) Your program asks classes student number XXX is taking, gets back
     a list of classes. No error.
-- 
        Ola Rinta-Koski                                 ···@cyberell.com
        Cyberell Oy                                     +358 41 467 2502
        Rauhankatu 8 C, FIN-00170 Helsinki, FINLAND	www.cyberell.com
From: Pierre R. Mai
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87k7vtsd40.fsf@orion.bln.pmsf.de>
·······@Yahoo.Com writes:

> Frode Vatvedt Fjeld <······@acm.org> wrote in message news:<··············@dslab7.cs.uit.no>...
> > To me that would be (at least in principle) a poorly specified
> > function that performs two unrelated tasks: Checking whether a student
> > exists and listing a student's current classes. Those should be
> > separate functions, and calling the latter function on an unknown
> > student would be an error (exceptional situation).
> 
> No no. Typically you don't want to have to shut down the whole University
> every time this program is run, to prevent somebody else from running
> a database update that installed a new student or removed an old student
> or corrected a mis-typed name by removing the mistaken student while
> adding the correctly-spelled named student. Scenerio:

If you have a database, then you'd better have a useful transaction
mechanism.  Cramming stuff into one function in the misguided belief
that this will magically solve your locking and transaction problems
is not the way to go.

If you are going to have true concurrent accesses, you will have to
lock the database data-structures, regardless, just in order to ensure
consistency of those data-structures.  CL implementations don't
generally guarantee the atomicity of either function calls or things
like gethash/(setf gethash)...

Regs, Pierre.

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: ·······@Yahoo.Com
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <ffdf399b.0201061908.24547e15@posting.google.com>
"Pierre R. Mai" <····@acm.org> wrote in message news:<··············@orion.bln.pmsf.de>...
> If you have a database, then you'd better have a useful transaction
> mechanism.

I agree. Furthermore it is NOT right for each workstation to directly
update pointers in the database. Rather there should be a database
server which accepts requests for information and/or updates, performs
the lookups and/or modifications, and returns a report of what realy
happened. For a counselor/advisor inquiring whether a given student
is taking such and such class, or asking what classes that student
is taking, this would typically be a SINGLE transaction, in English:
Requesting info about Mary Jones, list of classes. The return could
be any of:
- Not a registered student.
- Registered studnet, but not taking any classes currently.
- Registered student, and taking Math 103, English 101, Drams 107 ...
For registration wanting to correct a reeported mistake, this
would be two transactions, first the above, then a second which
makes the correction:
- For student number 3426786 or for Mary Jones, etc.
change second course from English 101 to English 102.
The report that comes back could be any of:
- No such student.
- Course 2 was not English 101, it was Drama 107
- Succssful update, course 2 is now English 102.
The workstation, whether it be the registrar, the President of the
University, or some random adademic advisor, never touches the database
directly, merely talks to the database server, rather like a Web server,
just a different syntax and semantics for selecting records and fields
within fields etc. (Actually an actual Web server could in theory handle
such a taski, and doing so isn't totally unreasonable.)

> Cramming stuff into one function in the misguided belief
> that this will magically solve your locking and transaction problems
> is not the way to go.

I disagree. Splitting the verification of existance of a record
from the actual update to that record, so it takes two transactions
instead of just one, in a distributed environment where the record might
cease to exist at any time (except in the middle of a single transaction
when the database server is dedicated to finishing that particular
transaction before starting another), and treating such ceasing of
existance of the record between the two calls as a fatal error requiring
reprogramming, is plain dumb. Students aren't deleted from their registration
every day, but during the first few weeks of classes both deletion of
registration (because the cheque for paying some student fee bounced,
or the student didn't show up for class, or the student was involved
in crime and banished from campus) is a *normal* thing that happens
from time to time and ought to be considered when designing the program,
and ought to be handled gracefully without having to shut down the
whole database system to fix a "bug". It isn't a bug. But a progarm that
checks for the record then updates the record in a separate transaction
*is* a poorly written program.

> If you are going to have true concurrent accesses, you will have to
> lock the database data-structures, regardless, just in order to ensure
> consistency of those data-structures.

Locking the whole database during the service of a single transaction
is reasonable. Breaking it up into two separate transactions and
locking the database during the entire time between the two transactions
is unreasonable. Checking the existance of the record, and reading
what's in it, should be a single transaction, not two separate
transactions. Likewise checking the existance and verifying the old
data is what needs to be changed and changing it to a new value should
be a single transaction not two or three.

> CL implementations don't
> generally guarantee the atomicity of either function calls or things
> like gethash/(setf gethash)...

That's no problem if the overall system is designed properly:
On the server end, a SINGLE program that fields service requests
and processes them one at a time, finishing each request (successfully
or not) before starting another.
To deal with the problem of some client starting to make a request then
taking a very long time to finish it, the server can READ but not yet
execute multiple incoming connections, and whichever finishes first
is moved to the queue for actual processing.
On the user side, any number of clients that have varying levels of
access priviledges for asking the server to do things, either just
read data or read and modify data. The program can be interrupted as
many times as happen during accepting input from a user, validating
that input, forming a service request to send to the server, and
transmitting that service request to the server. Then when the
service response comes back, that client program can again spend as
much time as it wants and be interrupted as many times as happens,
before it's finished presenting the results to the user for study.
To keep the server software simple, the database server should have
it's own special socket for queries, and listen on that socket itself,
rather than using the standard WebServer method of having a system program
start up a new copy of the server for each new connection. But a standard
WebServer like that *can* be used if it's programmed carefully: Each
clone of the WebServer application should have a unique ID, such as
the Unix process-ID (PID), and use that ID to make unique filenames that
aren't going to be stepped on by any other process, and then the main
database server can merely watch for the appearance of new files written
by those cloned WebServer applications, talk with those clones one by one,
and dismiss each such clone *after* all temporary files have been cleaned
up for that particular clone, so that there's no race condition with
a new clone happening to get the same PID as some old clone whose files
are not yet cleaned up.
Summary: I see no problem caused by CL in developing such a distributed
system, providing it's done the way I suggesed, a single service request
(transaction) for both check-if-record-exists and if-so-then-do-something-
with-it together.
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215443150672901@naggum.net>
* Bruce Hoult
| Here's what I don't get about CL confusing false and the empty list:  

  Please stop thinking of it as a "confusion", and you may get it.

| suppose you have a function (foo name) that returns a list of all the
| classes being taken by a student.  If the function returns NIL, does that
| mean that the student is taking no classes at the moment, or does it mean
| that the student doesn't exist?

  Well, read the documentation of the function to find out.  What else can
  there possibly be to say about this?  This is a non-existing problem.

  Since you think SQL's NULL is so great, do you get a NULL if the student
  whose classes you ask for does not exist?  Why would you ask for the
  classes of a non-existing student?   Not to mention, _how_?  Is a student
  somehow magically adressable?  In other words, what did you give that
  function as an argument to identify the student?

| It seems to me that using an empty list to represent NULL is just as bad.

  If you need to distinguish the empty list from NULL (nil) in the same
  function, your design sucks because you are confused, not the language.
  
///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Pierre R. Mai
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87vgg28fke.fsf@orion.bln.pmsf.de>
Bruce Hoult <·····@hoult.org> writes:

> Here's what I don't get about CL confusing false and the empty list:  
> suppose you have a function (foo name) that returns a list of all the 
> classes being taken by a student.  If the function returns NIL, does 
> that mean that the student is taking no classes at the moment, or does 
> it mean that the student doesn't exist?

How do you know that the function is going to return at all, if you
call it with the name of a non-student?  That's right, you will look
at the specification of that function.  And that's exactly where your
answer will be found.  If the author of the function cosidered it
useful to conflate "student doesn't exist, and therefore doesn't take
any courses" and "student exists, but still doesn't take any courses"
(which can be very useful in quite a number of occasions), then it
will return the empty list in either case, and the documentation will
state that.  Note that it would do this, even if NIL were unequal to
().  It is not trying to say don't know in the one case, and no
courses in the other, it is saying no courses in both cases, and that
is _exactly_ what it wants to say.

If the author thinks that those cases need to be distinguished, he has
any number of possible ways of communicating the difference.  For
example he can use mulitple values, with the secondary value
indicating whether the student existed at all.

But mostly, if the difference between non-existing and
existing-but-course-less students is really relevant, I'd specify foo
to signal an error if passed the name of a non-student.

> It seems to me that *every* datatype deserves to potentially have a 
> "don't know" or "doesn't exist" value.  Like NULL in SQL.  An integer 

[...]

> type.  How often do C programs fail because some function gets passed a 
> null pointer that didn't expect it?

This is a direct contradiction to your previous statement.  Either
every datatype deserves its own "don't know" or "doesn't exist" value,
which a null pointer in C arguably is, because it _can't_ clash with
any valid pointer value, or we forbid "don't know" values, because we
fear that receivers might not anticipate them and fail to handle them
correctly.  Making a distinction between NIL and () isn't going to
solve the problem of functions blowing up if they get NIL instead of
something they expected (like a person object), in fact it is going to
_worsen_ the situation, because all list processing functions know how
to deal with empty lists, but now that NIL != () they are _more_
likely to blow up if handed NIL, when they aren't going to expect it.

> It seems to me that using an empty list to represent NULL is just as bad.

Well, a lot of things seem to me to be the case, when I sit in my
armchair and muse about the state of the world.  Lucky for you I don't
share all of them with c.l.l.

Unless someone can demonstrate real problems when programming within
CL that are caused by (eq 'NIL '()), I consider it a worse problem
that so much time is wasted on discussing that non-issue, than any
problems that (eq 'NIL '()) could imaginably create, if it were indeed
a problem at all, which I don't see.

I think such issues should be decided based on some form of real-life
data, and not on armchair musing.

I have yet to see one bug that was caused by (eq 'NIL '()) tripping up
some minimally-competent programmer (i.e. one that didn't just start a
CL implementation by accident, when he really was expecting Scheme, or
some other language), or forcing someone to write noticably more
convoluted code because of it.

Regs, Pierre.

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-5733BD.18300523112001@news.paradise.net.nz>
In article <··············@orion.bln.pmsf.de>, "Pierre R. Mai" 
<····@acm.org> wrote:

> Bruce Hoult <·····@hoult.org> writes:
> 
> > It seems to me that *every* datatype deserves to potentially have a 
> > "don't know" or "doesn't exist" value.  Like NULL in SQL.  An integer 
> 
> [...]
> 
> > type.  How often do C programs fail because some function gets passed a 
> > null pointer that didn't expect it?
> 
> This is a direct contradiction to your previous statement.

No, it's an illustration of the dangers of not having a proper 
distinguished value for NULL.


> Either every datatype deserves its own "don't know" or "doesn't exist"
> value, which a null pointer in C arguably is, because it _can't_ clash
> with any valid pointer value, or we forbid "don't know" values, because
> we fear that receivers might not anticipate them and fail to handle them
> correctly.

There is a guarantee in C that no object has an address equal to the 
null pointer, but there is no type that says "this pointer points to a 
genuine object, and NOT to null".  That's the problem.  C++ tries to get 
around this using references, but even they can be subverted with a bit 
of hackery:

  struct foo {int x};
  foo *a = 0;
  foo &b = *a;

  b.x = 13;  // oops!


This can't happen in, say, Dylan because there are no null pointers.  If 
you have something like...

  define class foo(<object>)
     slot x :: <integer>;
  end;

  let a :: <foo> = ...;

  a.x := 13;

... then there is guaranteed to be no error in the assignment of 13 to 
a.x.

If you actually *want* to have a null value then you do it explicitly:

  let a :: type-union(singleton(#"null-value"), <foo>) = ...; 

Conventionally the null value used is always #f -- the canonical "false" 
-- and there is a standard function that makes it more convenient to 
create these union types:

  let a :: false-or(<foo>) = ....;

  when (a)
    a.x := 13
  end


> Making a distinction between NIL and () isn't going to
> solve the problem of functions blowing up if they get NIL instead of
> something they expected (like a person object),

It has no effect in that case.

> in fact it is going to _worsen_ the situation, because all list
> processing functions know how to deal with empty lists, but now
> that NIL != () they are _more_ likely to blow up if handed NIL,
> when they aren't going to expect it.

No, that's an improvement, because such a situation is a programming 
error, and you will now discover the error (and fix it) much sooner.


> > It seems to me that using an empty list to represent NULL is just as 
> > bad.
> 
> Well, a lot of things seem to me to be the case, when I sit in my
> armchair and muse about the state of the world.  Lucky for you I don't
> share all of them with c.l.l.

I didn't start this thread.

Furthermore, I have a lot of experience in a language in which a false 
value is not a list, so it's hardly armchair musing when I say that it's 
a damn good idea to separate the two notions.


> I have yet to see one bug that was caused by (eq 'NIL '()) tripping up
> some minimally-competent programmer (i.e. one that didn't just start a
> CL implementation by accident, when he really was expecting Scheme, or
> some other language), or forcing someone to write noticably more
> convoluted code because of it.

That's a great stock answer that can be used to justify any "feature" in 
any language or indeed application program. "If you were an expert in 
this program then you wouldn't have any problems.  How do we know if 
you're an expert?  Because you don't have any problems, of course!"

Cool.

Don't worry.  CL is totally perfect just as it is.  No other language, 
past, future or present ever had any idea better than the ideas already 
present in CL.  Where CL is more flexible than other languages it's 
because such complexity is necessary.  Where CL is more restrictive than 
othe languages it is because more generality is unnecessary.

I get it now.

-- Bruce
From: Pierre R. Mai
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87d7298u71.fsf@orion.bln.pmsf.de>
Bruce Hoult <·····@hoult.org> writes:

> There is a guarantee in C that no object has an address equal to the 
> null pointer, but there is no type that says "this pointer points to a 
> genuine object, and NOT to null".  That's the problem.  C++ tries to get 

That is a complaint about the weak type system that C has, which I can
sympathise with.  If I wanted to program in a statically typed
language, I'd want a type system that is at least as powerful as that
most modern functional programming languages enjoy, with type-inference
thrown in.

> > in fact it is going to _worsen_ the situation, because all list
> > processing functions know how to deal with empty lists, but now
> > that NIL != () they are _more_ likely to blow up if handed NIL,
> > when they aren't going to expect it.
> 
> No, that's an improvement, because such a situation is a programming 
> error, and you will now discover the error (and fix it) much sooner.

It isn't a programming error.  The callee is quite capable of handling
the empty list, and the caller has decided that it wants the NIL case
to be treated identically.  The callee doesn't have to be written to
handle the NIL case.

What is the fix? Instead of

(defun foo (x)
  (bar (list-or-nil-returner x)))

(defun bar (list)
  (dolist (elem list) (print elem)))

you want to see either

(defun foo (x)
  (let ((result (list-or-nil-returner x)))
    (bar (if (valid-p result) ;; Could be only result if NIL != ()
             result
             '()))))

(defun bar (list)
  (dolist (elem list) (print elem)))

or

(defun foo (x)
  (bar (list-or-nil-returner x)))

(defun bar (list-or-nil)
  (let ((list (if (valid-p list-or-nil) list-or-nil '())))
    (dolist (elem list) (print elem))))

I think the first replacement is the better one, if bar can be
specified to just handle lists.  But the fact of the matter is that
the original code is completely equivalent to that replacement, not
only in effect, but also in communicated intent.

> > > It seems to me that using an empty list to represent NULL is just as 
> > > bad.
> > 
> > Well, a lot of things seem to me to be the case, when I sit in my
> > armchair and muse about the state of the world.  Lucky for you I don't
> > share all of them with c.l.l.
> 
> I didn't start this thread.

So what?

> Furthermore, I have a lot of experience in a language in which a false 
> value is not a list, so it's hardly armchair musing when I say that it's 
> a damn good idea to separate the two notions.

But it is!  The experience you have in Dylan counts as zero when
discussing the problems of Common Lisp.  _They are different
languages_!  Language features aren't orthogonal, they live in the
ecology of a whole language.  Language feature A might be very
problematic in language 1, but pose no problems at all in language 2,
because it interacts very differently with other language features in
those languages, and with idiomatic programming in those languages.

So your experience with Dylan can support the claim "There is at least
one language where completely separating false and every other
datatype worked out great".  Since I don't have enough experience with
Dylan, I can neither refute nor confirm that claim for Dylan, but I
have used a number of other programming languages that did this, and
didn't find any problems with this approach.

What your experience doesn't support is the claim "(eq NIL ()) is a
problem in Common Lisp", or the broader claim "Identifying the false
value and some value of another datatype is wrong or problematic in
any language".

What my experience with CL does support is that (eq NIL ()) is not a
problem I have ever encountered in serious use of Common Lisp:

> > I have yet to see one bug that was caused by (eq 'NIL '()) tripping up
> > some minimally-competent programmer (i.e. one that didn't just start a
> > CL implementation by accident, when he really was expecting Scheme, or
> > some other language), or forcing someone to write noticably more
> > convoluted code because of it.
> 
> That's a great stock answer that can be used to justify any "feature" in 
> any language or indeed application program. "If you were an expert in 
> this program then you wouldn't have any problems.  How do we know if 
> you're an expert?  Because you don't have any problems, of course!"

Who said anything about experts?  I qualified my statement with
minimally competent, becaue we sadly get lots of people over here who
program in CL without having any knowledge of the language, assuming
they can just carry over their knowledge of Scheme, or some other
language.  I don't think the problems they present are to be taken
seriously.

If I were to start programming in Dylan, and stumbled across the
"problem" that Dylan seals its GFs by default, since I, not having
read anything about Dylan and blissfully assuming that this works
just like in CL, ran into large numbers of errors.  Now tell me, is my
having problems indicative of Dylan having a problem, or is it not
indicative of _me_ having a serious problem?

So we are not speaking about normal users having problems, we are
speaking about misguided individuals having problems.

> Don't worry.  CL is totally perfect just as it is.  No other language, 

It isn't.  There are a number of things that I find problematic.  One
such problem is the fact that LOOP is specified not to allow the
intermixing of VARIABLE-CLAUSES and MAIN-CLAUSES:

<quote hyperspec>
  loop [name-clause] {variable-clause}* {main-clause}*
</quote>

Since termination tests are part of the main-clauses, you can't write

(loop for x = (foo ...)
      while x
      for y = (do-something-with-non-null x)
      for z = (bar y)
      do
      ...)

This in itself causes one to write more convoluted code in such
situtions, especially if one can't fold the binding of y and z into a
LET construct, because one wants to use them in further loop clauses.

One of the better possibilities is

(loop for x = (foo ...)
      for test = (unless x (loop-finish))
      for y = (do-something-with-non-null x)
      for z = (bar y)
      do
      ...)

[Thanks Kent for reminding me about this possibility]

As I think you'll agree this is ugly, and non-obvious.

Furthermore this problem is aggravated by the fact that nearly all
LOOP implementations _do_ support this kind of intermingling, but
often without specifying the exact semantics of such a thing.  This
leads many people astray, blissfully assuming that it is well
specified portable code they are writing, until some new LOOP
implementation coughs at their code, hopefully producing warnings, but
possibly producing false iteration code instead.

And it isn't a problem that only seriously misguided people
encounter.  Even people well versed in the language make that slip
from time to time, as can be seen by the fact that Kent posted an
erroneous example only recently.  Same thing happened to me lots of
times, until I have become paranoid enough that I check every loop
form I stumble across for that mistake.  This is clearly an indication
that something is amiss here.

How to solve that problem is another question, of course.   Reopening
the standard is out of the question for some time to come, so some
other solution will have to be found.

> past, future or present ever had any idea better than the ideas already 
> present in CL.  Where CL is more flexible than other languages it's 
> because such complexity is necessary.  Where CL is more restrictive than 
> othe languages it is because more generality is unnecessary.

You seem to cling to the idea of a "perfect" language, and real
languages trying to approach that singularly-defined state of
perfection as a limit.

That is IMHO completely wrong.  Many, many decisions of languages have
to be judged subjectively by that language's community.

For example, Dylan is more static than CL in a number of areas, and
defaults to the static choice in a number of places (e.g. sealing GFs
by default).  So tell me, which is the better language, which made the
better choices?  I don't think this is a sensible question.  I think
CL made the correct choices with regards to the CL community, and
Dylan did so with regards to the Dylan community.  Neither is a priori
better than the other, they are different, because the members of
their communities value things differently, and likely also write
different programs.

That doesn't mean that it isn't possible to criticize a language, it
just means that you have to do it from the point of view of someone
writing non-trivial programs in it.

What would you think of a German, who came to England, and started to
criticize the English language based on the little he knows about it,
and the many great ideas that German qua language embodies?  The fact
that you can't just directly transplant language features from German
to English, and that things that would have been problems in German
aren't in English (and vice-versa), doesn't mean that one can't engage
in informed criticism of the language, it just means that one has to
inform oneself about the language, as used by the people, before one
can do so.

> I get it now.

I somehow doubt that very much...

Regs, Pierre.

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcvk7wgnedv.fsf@apocalypse.OCF.Berkeley.EDU>
"Pierre R. Mai" <····@acm.org> writes:

> You seem to cling to the idea of a "perfect" language, and real
> languages trying to approach that singularly-defined state of
> perfection as a limit.
> 
> That is IMHO completely wrong.  Many, many decisions of languages have
> to be judged subjectively by that language's community.
> 
> For example, Dylan is more static than CL in a number of areas, and
> defaults to the static choice in a number of places (e.g. sealing GFs
> by default).  So tell me, which is the better language, which made the
> better choices?  I don't think this is a sensible question.  I think
> CL made the correct choices with regards to the CL community, and
> Dylan did so with regards to the Dylan community.  Neither is a priori
> better than the other, they are different, because the members of
> their communities value things differently, and likely also write
> different programs.
> 
> That doesn't mean that it isn't possible to criticize a language, it
> just means that you have to do it from the point of view of someone
> writing non-trivial programs in it.
> 
> What would you think of a German, who came to England, and started to
> criticize the English language based on the little he knows about it,
> and the many great ideas that German qua language embodies?  The fact
> that you can't just directly transplant language features from German
> to English, and that things that would have been problems in German
> aren't in English (and vice-versa), doesn't mean that one can't engage
> in informed criticism of the language, it just means that one has to
> inform oneself about the language, as used by the people, before one
> can do so.

This is a very good analogue.  I started this strand of this thread,
not as a criticism of CL's design choice (which, in practice, works
just fine in CL, and has yet to cause me a practical problem), but
rather as a defense of another choice as reasonable.  I still think a
reasonable language, similar to CL, but differing in its goals, could
make the other choice without pain.

French has some very cool things that are missing from English.
Borrowing cool things where you can works out pretty well, in practice
(cf. the English language).  Trying to force the fundemental,
incompatible ideas of one language onto another just makes a mess (eg,
when people try to make English a Romance language), even if those
ideas were perfectly wonderful in the original language (cf. French).
Design choices cannot be made independently of one another, which
means there will never be a perfect language, any more than there will
be a perfect organism -- the best one can hope for is a perfect fit
for its environment/user-base.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Scott McKay
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <MhsL7.1926$oV2.890878@typhoon.ne.mediaone.net>
"Bruce Hoult" <·····@hoult.org> wrote in message
································@news.paradise.net.nz...
>
> It seems to me that *every* datatype deserves to potentially have a
> "don't know" or "doesn't exist" value.

I thought this for a short while designing Dylan, but I changed my
mind pretty quickly.  You can see where this leads with 'null' in
Java; Java's 'null' is, in some sense, typed, but the problem is that
'null' doesn't obey any of the protocols of the type.

Dylan has proper support for type unions, and we all realized that
'type-union(<integer>, singleton(#f))' -- or 'false-or(<integer>)',
since there's a standard extension macro -- is preferable.  It allows
the possibility of a "null" without all the headaches, and it means that
in the usual case you can generate tighter code.
From: Scott McKay
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <gwxL7.2785$oV2.1054016@typhoon.ne.mediaone.net>
"Scott McKay" <···@mediaone.net> wrote in message
··························@typhoon.ne.mediaone.net...
>
> "Bruce Hoult" <·····@hoult.org> wrote in message
> ································@news.paradise.net.nz...
> >
> > It seems to me that *every* datatype deserves to potentially have a
> > "don't know" or "doesn't exist" value.
>
> I thought this for a short while designing Dylan, but I changed my
> mind pretty quickly.  You can see where this leads with 'null' in
> Java; Java's 'null' is, in some sense, typed, but the problem is that
> 'null' doesn't obey any of the protocols of the type.

Who is this prat "SWM" and did he design Dylan?

Sorry -- I didn't design Dylan.  I meant "while Dylan was being
designed, I used to think this, too".  I do not mean to take credit
for the design of very much of the Dylan language.  Sorry.

> Dylan has proper support for type unions, and we all realized that
> 'type-union(<integer>, singleton(#f))' -- or 'false-or(<integer>)',
> since there's a standard extension macro -- is preferable.  It allows
> the possibility of a "null" without all the headaches, and it means that
> in the usual case you can generate tighter code.
>
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-092D6D.12470224112001@news.paradise.net.nz>
In article <·····················@typhoon.ne.mediaone.net>, "Scott 
McKay" <···@mediaone.net> wrote:

> "Bruce Hoult" <·····@hoult.org> wrote in message
> ································@news.paradise.net.nz...
> >
> > It seems to me that *every* datatype deserves to potentially have a
> > "don't know" or "doesn't exist" value.
> 
> I thought this for a short while designing Dylan, but I changed my
> mind pretty quickly.  You can see where this leads with 'null' in
> Java; Java's 'null' is, in some sense, typed, but the problem is that
> 'null' doesn't obey any of the protocols of the type.

You are mistaking my meaing.  Or I wasn't clear enough, or something.  
Null in Java is evil because there is no way to express the idea that 
you have a variable that is known to *not* be null.

What I want intead is a "null" value that is not in fact a member of 
*any* normal type, but which can be (OR ...)'d with any type to make a 
new type-that-includes-null.  The null value/type should not be a membe 
of any normal type, which means it should not be, for example, a valid 
list.

 
> Dylan has proper support for type unions, and we all realized that
> 'type-union(<integer>, singleton(#f))' -- or 'false-or(<integer>)',
> since there's a standard extension macro -- is preferable.  It allows
> the possibility of a "null" without all the headaches, and it means that
> in the usual case you can generate tighter code.

Yes, this is a beautiful thing, and highly practical.

The only downside is that Dylan doesn't then have a proper <boolean> 
type.  type-union(<boolean>, singleton(#f)) is the same as <boolean>, 
which is bad.  But it's better than the false value being a valid list.

-- Bruce
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215551923712524@naggum.net>
* Bruce Hoult
| You are mistaking my meaing.  Or I wasn't clear enough, or something.
| Null in Java is evil because there is no way to express the idea that you
| have a variable that is known to *not* be null.

  After a test for null, is that not precisely what you have?

| The null value/type should not be a membe of any normal type, which means
| it should not be, for example, a valid list.

  Could you _please_ start to explain _why_ these random things you keep
  carping about being "better" and "should" are just that?  All we get from
  you are random _conclusions_ and nothing at all to support them if one
  happens to disagree with those conclusions.  That _must_ mean there is
  absolutely nothing to them.

  Get over your personal hangup and just accept the language for what it
  is.  _Nothing_ will _ever_ happen to the language just because you keep
  having these problems.  Nobody is interested in your lack of will to
  accept the language while you are learning it.  It is fantastically
  annoying to have ignorant spluts keep arguing about things they do not
  like about the language.  What do you nutballs expect to happen?  Is this
  how you cope with _unchangeable_ things in general?  I do not expect you
  to accept any other people's decisions any more than that if* guy did,
  either, but it only makes you look _really_ stupid to those who manage to
  live with the language.  What do you _want_?  If you have no other mission
  here than to get "sympathy" for your personal problem of accepting what
  you cannot change, I think the whole thing really reeks.  Get over it and
  move on, or back to perfect Dylan or whatever the fuck you really need.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3BFF4A4B.FD9A2AE2@nyc.rr.com>
Did someone say "relax"?

Erik Naggum wrote:
> 
>  Could you _please_ start to explain _why_ these random things you keep
>   carping about being "better" and "should" are just that? ...
>   Get over your personal hangup....Nobody is interested in your lack of 
>   will...It is fantastically annoying to have ignorant spluts keep arguing
>   about things they do not
>   like...What do you nutballs expect to happen?...it only makes you look
>   _really_ stupid.....your personal problem of accepting what
>   you cannot change, I think the whole thing really reeks.  Get over it and
>   move on, or back to perfect Dylan or whatever the fuck you really need.

What justifies this bilious spew? Aside from it being great fun to write
and read.

Here is something I have practicing lately in professional email and NG
postings. After I write something I go back over and eliminate
everything in the second person from sensitive material. Programmers are
sensitive; our asses are always on the line. When code breaks, the
author gets beeped. Sometimes fired.

So where I have originally written "in convert-date-to-inches you use
the metric conversion..." I go back and change that to
"...convert-date-to-inches uses a metric conversion. maybe we should use
english...".

The article to which I respond uses the second person 23 times in
fourteen sentences (counting the third person bit about ignorant spluts
as 5). Ouch. Now excuse we while I go look up "splut".

kenny
clinisys
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215610939852273@naggum.net>
* Kenny Tilton
| [...] this bilious spew?  [...]

  Now your article looks much better, does it not?  Context be damned!  Let
  us all only select the individual words we do not like and respond to each.

  But to answer your stupid question: The text you elided in order to post
  your venomous response, of course.

  Learn to recognize a troll who is not after solving any problems, but
  only seeks _sympathy_ for his problems.  My guess is he only needs
  someone to say they agree with him that it is bad design to "confuse" the
  empty list and nil, and he will feel much better about himself.  What
  would actually _solve_ his problem, would, of course, be to _understand_
  the issue, but sympathy-seekers are prevented from understanding because
  there is no sympathy in understanding.  Understanding yields joy, not
  shared suffering -- that is the result of its opposite.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3C0315F3.DDF872AA@nyc.rr.com>
Erik Naggum wrote:
> 
> * Kenny Tilton
> | [...] this bilious spew?  [...]

That's a great compression algorithm, is it not? A little lossy in that
it tosses all civil discourse and keeps only the fighting words, but
there's the benefit, we don't have to wade thru the tedious material
stuff to get to the fireworks. Glad to see the 98% compression achieved
on my post.

> 
>   But to answer your stupid question: The text you elided in order to post
>   your venomous response, of course.
> 

Turn about is fair play, but FWIW my intent was pacifistic and
compassionate. And as a faithful reader of such threads I was honestly
puzzled as to how we got from zero to sixty in one article. Most folks
earn their incinerations by pursuing the threads beyond reason,
something not evident in this case.

>   Learn to recognize a troll...  

Fine, but missing from the above digest is my implication that a master
of relaxation would take such common NG conduct in stride.

[aside: the 2nd-Person scoring was off last time; it was the use
injunctions such as "Learn to..." that should count as five YOUs.]

It's a shame to see such incredible energy, devotion, and intellect
tilting at trolls, if*, and dictionary entries. I'd rather see a sit-in
staged at the most prestigious university not teaching Lisp. Students
would go crazy over a trash-talking, "bad boy" of computer science, John
McEnroe meets Sean Penn, high-intellect act.

You're the rock star of Common Lisp. Get your head out of c.l.l. and go
win us some converts.

kenny
clinisys
From: Janis Dzerins
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87bshojz8a.fsf@asaka.latnet.lv>
Kenny Tilton <·······@nyc.rr.com> writes:

> You're the rock star of Common Lisp. Get your head out of c.l.l. and
> go win us some converts.

I don't understand why some people are obsessed by the idea that
Common Lisp needs converts. I even think that converts that have to be
won should better stay away from Common Lisp.

-- 
Janis Dzerins

  Eat shit -- billions of flies can't be wrong.
From: Vebjorn Ljosa
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <cy3adx8ebfm.fsf@ljosa.com>
* Janis Dzerins <·····@latnet.lv>
| Kenny Tilton <·······@nyc.rr.com> writes:
| 
| > You're the rock star of Common Lisp. Get your head out of c.l.l. and
| > go win us some converts.
| 
| I don't understand why some people are obsessed by the idea that
| Common Lisp needs converts. I even think that converts that have to be
| won should better stay away from Common Lisp.

Hrmf.  Heretic. :)

-- 
Vebjorn Ljosa
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3C03717F.BAF8F29F@nyc.rr.com>
Janis Dzerins wrote:
> 
> Kenny Tilton <·······@nyc.rr.com> writes:
> 
> > You're the rock star of Common Lisp. Get your head out of c.l.l. and
> > go win us some converts.
> 
> I don't understand why some people are obsessed by the idea that
> Common Lisp needs converts. I even think that converts that have to be
> won should better stay away from Common Lisp.

I agree, actually. The unmentioned alternative to a university sit-in
would be simply to do great things with CL and not worry about what
other people think.

If CL had as many users as Java, Python, or Perl I think we would all
benefit, but I do not see that ever happening. I /do/ see other
languages continuing to pick up on CL features such as GC,
introspection, anonymous functions, GFs, macros so that if CL finally
dies it will have already been reborn in other HLLs.

kenny
clinisys
From: Janis Dzerins
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <877kscjw4p.fsf@asaka.latnet.lv>
Kenny Tilton <·······@nyc.rr.com> writes:

> Janis Dzerins wrote:
> > 
> > Kenny Tilton <·······@nyc.rr.com> writes:
> > 
> > > You're the rock star of Common Lisp. Get your head out of
> > > c.l.l. and go win us some converts.
> > 
> > I don't understand why some people are obsessed by the idea that
> > Common Lisp needs converts. I even think that converts that have
> > to be won should better stay away from Common Lisp.
> 
> I agree, actually. The unmentioned alternative to a university
> sit-in would be simply to do great things with CL and not worry
> about what other people think.

Oh, I see you're trying to be funny. But we don't have to dismiss
_all_ others. I just came up with a first criterion that people who I
would listen to would have to satisfy: they must have read at least
one standard (be it a programming language or community accepted
protocol, like most internet protocols) and don't complain about how
stupid one thing or another in it is (without having a better
solution).

> If CL had as many users as Java, Python, or Perl I think we would
> all benefit, but I do not see that ever happening. I /do/ see other
> languages continuing to pick up on CL features such as GC,
> introspection, anonymous functions, GFs, macros so that if CL
> finally dies it will have already been reborn in other HLLs.

And we especially don't need people talking about the death of Common
Lisp.

-- 
Janis Dzerins

  Eat shit -- billions of flies can't be wrong.
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3C039C3E.952F5C2A@nyc.rr.com>
Janis Dzerins wrote:
> 
> Oh, I see you're trying to be funny.

No, implicit in my suggestion was the energy I saw being misdirected at
defending CL, I gathered in the hope someday of greater use. Given that
goal apparently sought by others, I recommended more aggressive action
crucially outside c.l.l.

I am on the fence. I would love to see CL take over the world, but I am
not going to worry about it, I am just trying to do good work with CL.

And I definitely agree with the immediate point to which I responded:
too aggressive a netting might snare the wrong fish. CL would be wasted
on anyone who does not get it. But the only way to choose the few is to
call the many, perhaps with a bullhorn at some prestigious university.

> 
> And we especially don't need people talking about the death of Common
> Lisp.

CL is too good to be threatened by things like NG articles, and it is
too good to die. To die something better must come along, and that is
impossible because CL could become that better thing and do so better
than does the thing itself. Look at OO and CLOS. This is why Arc may be
a wrong turn.

kenny
clinisys
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215864060763152@naggum.net>
* Kenny Tilton
| No, implicit in my suggestion was the energy I saw being misdirected at
| defending CL, I gathered in the hope someday of greater use.

  Please let each person determine what is the "greater use" of their own
  energy, as long as it is not harmful.

| Given that goal apparently sought by others, I recommended more
| aggressive action crucially outside c.l.l.

  How do you know about happens outside c.l.l?  How would you discover that
  whatever it is you would recommend is actually done?

| I am on the fence. I would love to see CL take over the world, but I am
| not going to worry about it, I am just trying to do good work with CL.

  I would not like CL take over the world, because that which takes over
  the world, is taken over by the world.  Considering what the world does
  to other things it has taken over, it would be terrible, terrible fate.

| This is why Arc may be a wrong turn.

  I have briefly looked at Arc.  It is yet another demonstration of the
  problem of too strong an ego that cannot live with what somebody else has
  made.  Be it the standard conditionals, nil versus false versus the empty
  list, or whatever else this purportedly strong ego is too weak to accept,
  it is nothing more than proof of the core problem of the IT world -- the
  hardness of its pillars makes them brittle, not strong, so they cannot be
  used to build upon.  What was it that stood so much in the way that Paul
  Graham could not have accomplished it without creating a new language?
  Why was creating a new language and starting from scratch better than
  building on what had come before?  Why is the IT world defined by people
  who are unable to deal with the concepts of continuity, longevity, and
  design for long-term stability?  Why do they believe they are so much
  smarter than everything that has gone before them, when they clearly are
  not and repeat mistakes that take years to undo, if not replaced by
  another stupid "revolution" that itself starts from scratch?

  If people built societies the way computer people build communities, we
  would still live have small warring tribes and no concept of a law that
  binds all people and absolutely no concept of a constitution that binds
  lawmakers.  For all the talk about the Internet changing the world, we
  lag the real world by about 40,000 years when it comes to how we make
  lots of people who do _not_ agree to everything live and work together.

  Suddenly, I feel old and tired.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Wade Humeniuk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <9u0fal$tl6$1@news3.cadvision.com>
>
> | This is why Arc may be a wrong turn.
>
>   I have briefly looked at Arc.  It is yet another demonstration of the
>   problem of too strong an ego that cannot live with what somebody else
has
>   made.  Be it the standard conditionals, nil versus false versus the
empty
>   list, or whatever else this purportedly strong ego is too weak to
accept,
>   it is nothing more than proof of the core problem of the IT world -- the
>   hardness of its pillars makes them brittle, not strong, so they cannot
be
>   used to build upon.  What was it that stood so much in the way that Paul
>   Graham could not have accomplished it without creating a new language?
>   Why was creating a new language and starting from scratch better than
>   building on what had come before?  Why is the IT world defined by people
>   who are unable to deal with the concepts of continuity, longevity, and
>   design for long-term stability?  Why do they believe they are so much
>   smarter than everything that has gone before them, when they clearly are
>   not and repeat mistakes that take years to undo, if not replaced by
>   another stupid "revolution" that itself starts from scratch?
>

I went to an OO conference in Santa Clara,1991.  At lunch time I sat down
with this older gentleman, maybe in his fifties.  The first thing he asked
me was, "We are a Cobol shop, have been for a long time, I am here to see if
we have to change.  Things seem to be working fine for us.  Do you think we
have to change?".  Now, not knowing Cobol, and thinking for literally 2
seconds I said "No."  He seemed immensely relieved and I am sure that he
went back and continued  in Cobol.

There is alot to be said for sticking with an approach and not giving into
the calls to change everything.  Computing seems to have really hard hit by
this reinvention syndrome, maybe because its largest group of developers are
young competitive men.  Trying to kill the older males off I suppose,
primevel instincts coupled with above average intelligence.  Driving them
off the "kill" (so to speak).  Maybe Microsoft is successful since Gate's
personality is strong enough to subdue the rabble at the gates (eheh, images
of Frankenstein come to mind).  Perhaps the young males energies should be
harnessed into much more difficult projects until they mellow out a bit.

Wade
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcvzo57fzm5.fsf@conquest.OCF.Berkeley.EDU>
Janis Dzerins <·····@latnet.lv> writes:

> Kenny Tilton <·······@nyc.rr.com> writes:
> 
> > You're the rock star of Common Lisp. Get your head out of c.l.l. and
> > go win us some converts.
> 
> I don't understand why some people are obsessed by the idea that
> Common Lisp needs converts. I even think that converts that have to be
> won should better stay away from Common Lisp.

That's unnecessarily elitist.  I don't think that Lisp needs everyone
who can write a line of code, but there are a lot of people who,
without effort from others, wouldn't even know that Lisp exists (in
its modern form).  And, even if they do, there are a *lot* of cool
things to learn, and if they don't have any idea how good CL is, how
will they know to prioritize learning it?  I don't want every
halfway-stupid Perl hacker working in Lisp.  I do want a lot of people
who are very intelligent, concentrating on other things, and fighting
against their language, without realizing the extent to which they can
do something about that, to learn Lisp.  How did you learn that Lisp
was worth learning (instead of doing whatever else you could have used
the same time for)?  Being at the right place at the right time?
Concerted evangelism?  Both?  If it hadn't been for a stroke of luck,
I'd be working on C++ compilers now, because I wouldn't have realized
the extent to which a language could work with me.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Janis Dzerins
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87wv0bi0rv.fsf@asaka.latnet.lv>
···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) writes:

> Janis Dzerins <·····@latnet.lv> writes:
> 
> > Kenny Tilton <·······@nyc.rr.com> writes:
> > 
> > > You're the rock star of Common Lisp. Get your head out of c.l.l. and
> > > go win us some converts.
> > 
> > I don't understand why some people are obsessed by the idea that
> > Common Lisp needs converts. I even think that converts that have to be
> > won should better stay away from Common Lisp.
> 
> ...

> I do want a lot of people who are very intelligent, concentrating on
> other things, and fighting against their language, without realizing
> the extent to which they can do something about that, to learn Lisp.

This is how I _finally_ decided to switch to Common Lisp. But this is
not a "winning coverts" thing. It is a "there must be a better way"
thing that people must come to themselves.

> How did you learn that Lisp was worth learning (instead of doing
> whatever else you could have used the same time for)?

The enlightenment does not come in one day. That's the reason that
people who switch to Lisp because someone told it's "way cool" won't
work.

> If it hadn't been for a stroke of luck, I'd be working on C++
> compilers now, because I wouldn't have realized the extent to which
> a language could work with me.

The best thing that can be done about this is to make people aware of
Common Lisp. If they are at least a bit intelligent they will look
into it and find for themselves whether it is worth learning.

-- 
Janis Dzerins

  Eat shit -- billions of flies can't be wrong.
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215856216416619@naggum.net>
* Kenny Tilton <·······@nyc.rr.com>
| Turn about is fair play, but FWIW my intent was pacifistic and
| compassionate.

  Yes, intent is all that counts.

| And as a faithful reader of such threads I was honestly puzzled as to how
| we got from zero to sixty in one article. Most folks earn their
| incinerations by pursuing the threads beyond reason, something not
| evident in this case.

  Huh?  Bruce Hoult has been carping on the same stupid "confusion" for
  years.  Nothing ever happens.  No understanding.  Just pauses between
  reiterations and regurgitations of the same stale arguments.

| You're the rock star of Common Lisp. Get your head out of c.l.l. and go
| win us some converts.

  As most rock stars, I think I should go despair about my popularity.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3C03A302.4621738C@nyc.rr.com>
Erik Naggum wrote:
> 
>   Huh?  Bruce Hoult has been carping on the same stupid "confusion" for
>   years.  

Oh, OK. Sometimes the existence of a certain amount of history is
apparent in these threads, this time I did not pick that up.

kenny
clinisys
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87y9ksguai.fsf@teonanacatl.andreas.org>
Erik Naggum <····@naggum.net> writes:

>   Get over your personal hangup and just accept the language for what it
>   is.  _Nothing_ will _ever_ happen to the language just because you keep
>   having these problems.  Nobody is interested in your lack of will to
>   accept the language while you are learning it.  It is fantastically

Can anybody explain to me why some people regard the Common Lisp
standard as gospel?  What happened to the spirit of continuous
improvement that has led Lisp through the decades?

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215865367762047@naggum.net>
* Erik Naggum
> Get over your personal hangup and just accept the language for what it
> is.  _Nothing_ will _ever_ happen to the language just because you keep
> having these problems.  Nobody is interested in your lack of will to
> accept the language while you are learning it.

* Andreas Bogk
| Can anybody explain to me why some people regard the Common Lisp standard
| as gospel?

  Well, why do you regard it as gospel?  Why do _you_ think in such terms?
  Explain this, and you will be much closer to the wisdom you seek.

| What happened to the spirit of continuous improvement that has led Lisp
| through the decades?

  The keyword here is "continuous".  At some point, some people decided
  that the only way to achieve improvement would be through discontinuity
  and revolution, through many meaningless changes they could achieve some
  small meaningful one.  These people have only succeeded in one thing: To
  instill this meme in so many people that they do not even _try_ to make
  continuous improvements, anymore.  Whey they fail again and again to
  achieve improvement with their revolutions, they argue that stronger and
  more powerful revolutions are necessary, when in fact it was the idea
  that revolutions are necessary that caused them to fail.  Smaller egoes
  and more purpose would have made them succeed, because what they need to
  succeed with is not to build a whole new world from scratch, but to make
  those who already live in one to accept their improvements.  If they do
  not, accept that, too, and try again.  Accepting defeat is perhaps the
  only true evidence of personal strength.  Refusing to accept defeat and
  believing that if you only try the exact same thing again over and over
  you will some day get a different result, is simply the insanity of weak
  minds that refuse to let go of their one chance at success and greatness.

  Every bit of progress has cost thouands of setbacks, but each did in fact
  not set the whole industry back because one did _not_ start from scratch
  with every "invention".  Because of the continuity, one built upon what
  already existed and found an acceptable way to achieve one's goal until
  the underlying changes were being made by those who were motivated by the
  success of the visible changes.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87vgfwf5jj.fsf@teonanacatl.andreas.org>
Erik Naggum <····@naggum.net> writes:

> | Can anybody explain to me why some people regard the Common Lisp standard
> | as gospel?
>   Well, why do you regard it as gospel?  Why do _you_ think in such terms?

I don't.  I suggested that you do, based on your "it is the way it is,
get over with it" argument.

Dylan was designed based on the experience with other Lisp
designs. When I see a difference between the way CL does something,
and the way Dylan does it, I ask myself if this is by design or by
accident, and whether the modification is the Right Thing or the Wrong
Thing.  It is interesting to get the opinions of seasoned CLers on
these features, even if I have a bias from my prior experience and
might not agee with them.  After all, everyone is biased.

>   Explain this, and you will be much closer to the wisdom you seek.

Ho-hum.  I guess I'll have to wait for your answer before
enlightenment sets in.

> | What happened to the spirit of continuous improvement that has led Lisp
> | through the decades?
>   The keyword here is "continuous".  At some point, some people decided
>   that the only way to achieve improvement would be through discontinuity
>   and revolution, through many meaningless changes they could achieve some
>   small meaningful one.  These people have only succeeded in one thing: To
>   instill this meme in so many people that they do not even _try_ to make
>   continuous improvements, anymore.  Whey they fail again and again to
>   achieve improvement with their revolutions, they argue that stronger and
>   more powerful revolutions are necessary, when in fact it was the idea
>   that revolutions are necessary that caused them to fail.  Smaller egoes

I'm from East Germany, and have been there when the Berlin Wall came
down.  Don't tell me revolutions don't happen, I have been part of
one.

But I think your general insight is correct, there ought to be a
balance of change.  Both lack of change and too much change are
dangerous to the stability of a system.

What I am perceiving (and this is as subjective as it gets) is a lack
of change.  

>   and more purpose would have made them succeed, because what they need to
>   succeed with is not to build a whole new world from scratch, but to make
>   those who already live in one to accept their improvements.  If they do

Again an interesting observation.  Let me know, what change would you
accept?

>   not, accept that, too, and try again.  Accepting defeat is perhaps the
>   only true evidence of personal strength.  Refusing to accept defeat and
>   believing that if you only try the exact same thing again over and over
>   you will some day get a different result, is simply the insanity of weak
>   minds that refuse to let go of their one chance at success and greatness.

It is only insanity if you don't learn from your failures, and don't
get a different result next time.  Maybe you won't succeed, because
the challenge is bigger than a lifetime, but that doesn't mean trying
is futile.  Unless, of course, you hide your results from the world.

I'd even go as far as saying that *only* failures lead to genuine
insight, whereas a success is just a validation of your current model
of the world, and not an improvement.

>   Every bit of progress has cost thouands of setbacks, but each did in fact
>   not set the whole industry back because one did _not_ start from scratch
>   with every "invention".  Because of the continuity, one built upon what
>   already existed and found an acceptable way to achieve one's goal until
>   the underlying changes were being made by those who were motivated by the
>   success of the visible changes.

I agree.  But I think we currently disagree on what part of the model
to keep, and what to change.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215910318983115@naggum.net>
* Andreas Bogk
| Can anybody explain to me why some people regard the Common Lisp standard
| as gospel?

* Erik Naggum
> Well, why do you regard it as gospel?  Why do _you_ think in such terms?

* Andreas Bogk
| I don't.  I suggested that you do, based on your "it is the way it is,
| get over with it" argument.

  I repeat: Why do you think in such terms?  Your suggestion is nothing but
  a way to tell the world that you conceptualize in terms of "gospel" and
  other religious terms.  _Why_ do you do this?  What purpose does such a
  conceptualization serve?  What kind of short-circuiting of your thinking
  processes are you satisfied with once you can label someone "religious"?
  I am interested in _why_ you have this conceptualization.  If you do not
  even recognize that in order to accuse somebody else of something when
  lacking evidence of it _from_ those you accuse, i.e., you must recognize
  that the "pattern" you see is your own mental creation, you have to think
  in the terms you accuse them of, please let me know that you do not even
  consider _yourself_ worth listening to, and I shall comply with that.

  There are a few things that are never true of "me", only of "you", in the
  words and opinions and thinking patterns of some people.  Those who make
  that mistake, provide the world with evidence that they cannot consider
  what it would mean for someone for their accusations to be true, hence
  they are worthless nonsense published only to pester and annoy people,
  because they, too, _know_ that it is untrue.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <878zcrc59s.fsf@teonanacatl.andreas.org>
Erik Naggum <····@naggum.net> writes:

> > Well, why do you regard it as gospel?  Why do _you_ think in such terms?
> | I don't.  I suggested that you do, based on your "it is the way it is,
> | get over with it" argument.
>   I repeat: Why do you think in such terms?  Your suggestion is nothing but
>   a way to tell the world that you conceptualize in terms of "gospel" and
>   other religious terms.  _Why_ do you do this?  What purpose does such a

Because that's the association I have when reading your arguments.
The "you must believe in it, because it was written by God^Wpeople
much smarter than you" argument.  The "it's not Lisp unless it is
Common Lisp, and everybody deviating from Common Lisp is a heretic,
even if he doesn't claim

>   conceptualization serve?  What kind of short-circuiting of your thinking
>   processes are you satisfied with once you can label someone "religious"?

I can stop trying to have a rational argument with them about the
subject of their belief.  I might try to start a religious argument,
but that's an entirely different game.

>   I am interested in _why_ you have this conceptualization.  If you do not
>   even recognize that in order to accuse somebody else of something when
>   lacking evidence of it _from_ those you accuse, i.e., you must recognize
>   that the "pattern" you see is your own mental creation, you have to think
>   in the terms you accuse them of, please let me know that you do not even
>   consider _yourself_ worth listening to, and I shall comply with that.

I'm not lacking evidence, there's enough in your postings.  If I sound
like a religious zealot to you (which of course is just a pattern in
*your* brain), and if you think religious discussions are pointless,
stop listening to me.  All else would be a waste of time and bandwidth.

>   There are a few things that are never true of "me", only of "you", in the
>   words and opinions and thinking patterns of some people.  Those who make
>   that mistake, provide the world with evidence that they cannot consider
>   what it would mean for someone for their accusations to be true, hence
>   they are worthless nonsense published only to pester and annoy people,
>   because they, too, _know_ that it is untrue.

I'm only reporting my impressions, honestly and faithfully.  If this
annoys you, maybe you should search the reason on your side.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215965920426322@naggum.net>
* Andreas Bogk
| Because that's the association I have when reading your arguments.

  Precisely.  This is your problem, and you should just go fix it.  Nobody
  is so fucking stupid as to regard a standard as "gospel".  Grow a clue.

| The "you must believe in it, because it was written by God^Wpeople much
| smarter than you" argument.

  Where is the "believe in" part outside or your mind?  Just because you
  have a personal problem with your incredibly low reading comprehension
  and an overactive imagination that fills in the blanks when you do not
  understand what you read, does not give you the right to assume that you
  reach valid conclusions.  In fact, it is typical of inferior thinking
  skills that you _do_ think you can fill in the blanks and reach any
  goddamn conclusion you want.  Rational people do not lie about their
  observations in order to arrive at their pre-conceived conclusions.

| The "it's not Lisp unless it is Common Lisp, and everybody deviating from
| Common Lisp is a heretic, even if he doesn't claim

  Nobody says this, either, you dimwit.  Notice how you introduce all the
  religious terms -- because that is _your_ language.

>  What kind of short-circuiting of your thinking processes are you
>  satisfied with once you can label someone "religious"?

| I can stop trying to have a rational argument with them about the subject
| of their belief.

  But because _you_ make up your mind that somebody is religious, and you
  are the first to relinquish rational argument, _you_ are in fact the only
  irrational and religious person around.  You will never understand this,
  any more than most criminals accept that they are guilty.

| I'm not lacking evidence, there's enough in your postings.

  Only for the association in _your_ mind.  That has nothing at all to do
  with me.  For all your fascination with logic, you sure do not know how
  to arrive at valid premises.   When you accuse me of something when in
  fact you are only accusing me of causing associations in a deranged and
  religious mind, it is important to point out that every monster you see
  is your own creation.  Religious people, especially those who have turned
  their back to religion for the wrong reasons and who have a huge personal
  authority problem as a result, tend to assume that _all_ authorities are
  religious in nature, or want to be.  This happens only to stupid people
  who are too goddamn slowwitted to figure out what they really object to.
  Because they can label everything they do not like "religious" after this,
  they will also never mature or develop beyond this infantile rejection of
  authority.  In short, mentally underdeveloped and rebellious children.

| If I sound like a religious zealot to you (which of course is just a
| pattern in *your* brain), and if you think religious discussions are
| pointless, stop listening to me.

  A person who talks about "gospel" is ipso facto a religious zealot.

| I'm only reporting my impressions, honestly and faithfully.

  My _impression_ of you is that you are probably the stupidest person to
  come visit us in several months.  What value does this impression have?
  Should I share it with anyone?  I am trying to cause you, the stupidest
  person around, to revv up your dysfunctional brain and stop accusing
  people of your own mental problems that cause you to think anybody but
  you think in terms of religion and gospel.  This is _your_ problem, and
  only _you_ can solve it.  Here is how: Figure out that people who look
  religious to _you_, are in fact _not_.  Then read my signature and be
  enlightened, or at least start to think.

| If this annoys you, maybe you should search the reason on your side.

  Of course, it is also Common Lisp's fault that you have problems with it.

  Dylan seems to breed clueless idiots faster than applications.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcvn11cnf5b.fsf@apocalypse.OCF.Berkeley.EDU>
Bruce Hoult <·····@hoult.org> writes:

> In article <···············@shell01.TheWorld.com>, Kent M Pitman 
> <······@world.std.com> wrote:
> 
> > we have a 25-or-so year history
> > during which both Scheme and CL have existed, and in no cases have I
> > ever seen or heard of someone tearing out their hair and leaving the
> > CL community saying "I just can't build complex programs because this
> > NOT/NULL [or false/empty-list] thing is making it too hard to write
> > metaprograms".  It just doesn't happen.  So no one ever points to that
> > as the reason for splitting false/empty-list.  They point instead into
> > the murky depths of the human brain, citing simplicity without
> > defining their simplicity metric
> 
> Here's what I don't get about CL confusing false and the empty list:  
> suppose you have a function (foo name) that returns a list of all the 
> classes being taken by a student.  If the function returns NIL, does 
> that mean that the student is taking no classes at the moment, or does 
> it mean that the student doesn't exist?

Well, that's a lousy interface (to the function foo).  I can see two
good ways to fix it:

  1. FOO returns two values, the first being the list, the second
     being a boolean, true if the student was found, as with GETHASH.

  2. FOO returns the list, and signals an error if the student is not
     found.  If the caller is expecting there to be a high proportion
     of unknown students, the cost of this situation can be reduced
     somewhat by having the keyword arugments :error-p and
     :error-value, as with READ.

One thing that's very nice about having a Really Big language is that
(iff it's well-designed, as CL is) the language itself offers good
design examples.  If you're having a problem expressing something,
first see if CL deals with similar situations, and see how it deals
with them.  (AMOP is also quite good for this).

As I said before, the NIL-the-symbol/NIL-the-boolean/NIL-the-empty-list
thing causes occasional philisophical angst for me, but no practical
problems that good design couldn't solve.  

> It seems to me that using an empty list to represent NULL is just as bad.

Er, I hope you meant "to represent false", because null-ness is a
property of lists (or sets, or ...), not booleans.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Boris Schaefer
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87n11bkd8z.fsf@qiwi.uncommon-sense.net>
* Bruce Hoult <·····@hoult.org> wrote:
| 
| Here's what I don't get about CL confusing false and the empty list:
| suppose you have a function (foo name) that returns a list of all
| the classes being taken by a student.  If the function returns NIL,
| does that mean that the student is taking no classes at the moment,
| or does it mean that the student doesn't exist?

I don't think your problem is with CL "confusing" false and the empty
list.

Suppose you have a function (takes-class-p name class), that checks
whether a student takes a specific class at the moment.  If the
function returns NIL, does that mean that the student is not taking
that class at the moment, or does it mean that the student doesn't
exist?

I think your problem is with bad documentation.

Boris

-- 
·····@uncommon-sense.net - <http://www.uncommon-sense.net/>

Laugh and the world thinks you're an idiot.
From: ·······@Yahoo.Com
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <ffdf399b.0112101733.e43df44@posting.google.com>
Bruce Hoult <·····@hoult.org> wrote in message news:<···························@news.paradise.net.nz>...
> Here's what I don't get about CL confusing false and the empty list:
> suppose you have a function (foo name) that returns a list of all the
> classes being taken by a student.  If the function returns NIL, does
> that mean that the student is taking no classes at the moment, or does
> it mean that the student doesn't exist?

I agree with your assumption that for synchronization with a dynamically
shared database you want a SINGLE function to call to check if the student
exists and if so then check his/her classes, rather than two different
function calls in a block of DISABLE-INTERRUPTS or FREEZE-THE-WORLD.
Let the synchronization be handled inside the service routine rather
than by each and every programmer attempting to call it.

Given that assumption, CL has several tools available to use, and it
is up to the programmer to decide which he/she prefers to use:
- Return two values, one of which says whether student exists or not,
and other value says list of classes (which is indeterminate or
meaningless if the student doesn't exist).
- Set up your own special token such as NOSUCH to indicate there's
no such student as opposed to a student that exists but isn't taking
any classes.  (READ Stream EOFerrorP EOFvalue) is an example of a
built-in function that uses a strategy vaguely like this if EOFerrorP=NIL.
- Throw something to a catcher or signal a normal error if there is
no such student, like READ if EOFerrorP is non-null.
- Return a list that is one longer than the number of classes, where
the CAR is the student ID number and the CDR is the actual list of
classes, but if no such student then return NIL instead of list of one element.
* Remember, as programmer you get to choose which way to write your
database-lookup utility, and LISP provides sufficient primitives to make
it easy to do it any of several ways.

> It seems to me that *every* datatype deserves to potentially have a
> "don't know" or "doesn't exist" value.  Like NULL in SQL.

Global symbols can be bound or unbound, where unbound is somewhat like your
"don't know" state. If you want to directly make use of that facility
for your application without making ugly side-effects, you can use GENSYM
or similar facility to make a new identifier then pass the name of that
to your database-lookup utility, which will either make that symbol unbound
or make it bound with the list of courses or count of courses, and
then the calling function can call BOUNDP first to see whether it's
bound or not. Unlike returning two values, by this method you can keep
that non-interned symbol around and link to it from several places at
once and thereby share both whether student exists and if so course info,
and furthermore you can attach other properties to that same uninterned
symbol as you proceed with processing that person's application for whatever
prompted you to search for his/her student record.

> ... or can be declared to be NOT NULL
> and this is an important distinction.  In any complex program some code
> needs to be written to cope with NULL values, and some code wants to
> assume that there is always valid data.

Any place in your program you're not sure if you've already tested for
existance of the student, and you want to proceed with confidence the
student really does exist, you can test whatever convention you have
programmed for non-existance and if so then signal an ERROR. So if
you indeed have goofed somewhere, you'll get a nice clean message that
student doesn't exist when we assumed he did, instead of some obscure
message about attempt to take CDR of a non-list.
From: ·······@Yahoo.Com
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <ffdf399b.0112101658.29b684de@posting.google.com>
Kent M Pitman <······@world.std.com> wrote in message news:<···············@shell01.TheWorld.com>...
> The Scheme community then works to minimize the number of premises
> they work from, as if minimizing this one axis in what is obviously a
> multivariate system will yield a consequent minimization of the other
> axes by magic.

When you are first starting to learn something new, the fewer things
you must learn just to get started the easier it is to get started.
I'm not saying Scheme starts with the right stuff, see later...

> ...  THat is, a language that has has
> all 64 crayola crayon colors as primitive concepts is at a marked
> advantage for describing a sunset over one that has only the primary
> colors plus the modifier words "saturated", "bright", "dark" and
> adverbials like "not" and "very".

Agreed, but for an absolute beginner it's easier to get started with
only the primary colors, then the concept of mixing them together,
and lastly the other modifiers, before you start the horrendous task
of memorizing al those other specialized color names. The trick is
to have a system where you can start with just the simple stuff then
grow from there until you have learned how to keep track of and use
a wide range of 'utilities' (things you can rely on, like electricity,
telephone, water, mapping between name and color in crayon box, etc.).

> Now, second, the Scheme community has another very unwarranted premise
> underlying a great deal of its teaching, and it overflows sometimes
> into design: that's that if they can find a simpler way to express
> things (using their simplicity metric: smaller language) that this
> will autmatically lead something to be easier to learn.

If you're learning something consistent, such as mathematics or
computer programming, it's nice when first starting to have a minimal
set of utilities you must learn and then to re-invent the wheel
a few times to get a feel for the expressive power of that minimal
language. For example, our Arabic number system whereby we must learn
the digits 0123456789 plus the rule for values from the right being
ten times as large, and later the decimal point with values to the
right being only one tenth as large, is relatively simple compared to
a system where each different size had a different name with no pattern
for linking them together, such as fluid-ounces cups pints quarts gallons
barrels etc.

To my mind, computer programming consists of making use of already
existing utilities (written by other people), putting usages of such
utilities in sequence (*) so that output from an early-used one can
then be taken as input by a later-used one, and collecting such sequences
together under a single name thereby creating your own utility to
adjoin to the set of available utilities. For absolute beginners,
it seems to me the best way to reduce these concepts to essentials
and make them patently obvious to the student, and simultaneously
minimize the amount that must be learned to get started, is to use
PROG (with labels and GO and RETURN), SETQ (or SETF), and DEFUN,
as the only primitives for putting together sequences. Show the student
how to make calls to existing utilities that do the sorts of things
you'd expect to be doable on a computer (making arithmetic calculations,
searching strings for specific characters or kinds of characters).
Show the student how to assign results to variables via SETQ so the
result doesn't get lost and you can call it back in later. Show the
student how to break a simple task into pieces each of which is doable
by Common LISP built-in utilities, which involves making several function
calls and doing SETQ of the result of each and re-using each (except
the last) in later function calls. Show the student how to make a
function (using DEFUN) containing a canned sequence (via PROG) of
function calls which has a name so you can do that sequence as many times
as necessary. Here's a simple task that would be suitable for such a
very first programming lesson: Find the first number within a string:
Call POSITION-IF to find the index of the first digit. Call POSITION-IF-NOT
to find the index of the end of those consecutive digits. Call SUBSTR
using the two previous results to extract just those digits. RETURN
that sub-string of digits. If the result is wanted as an actual LISP
number then insert a call to PARSE-INTEGER after the SUBSTR before
the RETURN. After that basic understanding of sequence of function calls
is understood, then the student is ready to learn all the "better" things
such as nested function calls, and the technique of program loops,
and then the "better" way of expressing many program loops via the
LOOP or MAP etc. utilities, and someday the "better" way of doing many
local variables via LET instead of PROG and SETQ..

* (Sequence as used here is more general than the linear sequences
which are a data type in Common LISP. It's more like a directed graph,
also known as a flowchart.)

In summary, I think simple function calls, SETQ, PROG, and DEFUN,
in that sequence, are a very tiny number of concepts to learn yet
are effective in teaching the essence of computer programming
as well as excite the student about many of the wondrous utilities that
are built into Common LISP already. Every other utility in CL can
be treated on an as-needed basis. Like if you're searching for stuff in
strings, then you learn some of the string utilities such as POSITION-IF,
while if you're making arithmetic calculations you learn some of the
arithmetic functions such as + and >=. This method makes LISP programming
easier than Web browsing where you must learn how to click on links,
how to back up to where you were before, how to scroll, how to
select various windows that might be hidden behind others, how to save
bookmarks, how to use bookmarks later, how to resize windows, and how to
use the various search engines for finding starting points for effective
browsing.

> ...  I
> think people have a highly parallel associative mechanism capable of
> efficiently managing an enormous amount of special cases at the same
> time.

Eventually, but not right at the start when learning a new kind of task
such as foreign language or how to program computers.

> But to me, the issue of what makes a language easy/hard to use is the
> dissonance between the mental representation of the user and the
> manifest structure of the program.

I agree very much. That's why I like PROG as a starting point, because
I think of doing this first, then using that to do this next, etc.,
and PROG expresses that nicely. PROGN would work as well, except it
doesn't have a place to declare local variables, and it takes one more
character to type the name (minus three characrters for space and ()
for empty argument list, so that's not really an argument). The average
person knows that a cooking recipe is a sequence: Boil 6 cups water.
Stir in macaroni. Boil 7-10 minutes. Drain water. Return macaroni
to pan. Stir in margarine milk and cheese powder. It's implicit that
the boiling water is used as input for stiring macaroni, and that combo
is passed through boiling and used as input for draining, etc.
In computer programming you just make it explicit what outputs from
earlier steps go as inputs to later steps, which makes it actually easier
than cooking in some sense.

Later after the student has programmed a couple PROG GO loops, we can
show how a LOOP or MAPLIST better matches the overall concept of what we
are trying to accomplish. Then we can introduce even more powerful
utilities such as SET-DIFFERENCE which are very simple mathematically
conceptually yet nontrivial to manually code with PROG or LOOP or MAPLIST.
The great thing about LISP is we can start with just four primitives and
everything else as-needed, doing everything from those barebones primitives,
then gradually learn about already-existing utilities that do most of
the low-level work for us. We don't have to learn the whole thing just
to get started, and the starting set to learn is VERY VERY small yet
universal in power if we allow some basic utilities for any given
data type we choose to deal with at any given time.

> ...  I'm not trying to argue CL
> is an utterly simple language to learn and use.

Well, I'm arguing that, in the sense you can start very very simple
then learn new parts of the language on an as-needed basis, and the
manual is nicely organized around data types so it's easy to look up
any built-in utility you need for any desired task, to see how much
is already available and how much you still need to program yourself
on top of the built-in utilities.
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215429831639397@naggum.net>
* Thomas F. Burdick
| I don't know that the problem is the inexperienced user.

  I think it is.  Some people insist on being inexperienced despite their
  experience.  I think this is a stupid kind of stubbornness, but we find
  it in a number of people.

| But our current conception of evolution could very well be off, and I
| don't think it takes a genius to figure out that English is a crazy (if
| practical) language.

  But it takes a really smart person to accept it for what it is and not
  nurture a desire to change the grammar.  The same is true for medicine.
  It is pretty easy for anyone who is studying anatomy to figure out ways
  that the human body could be improved.  Fortunately, the ethical
  standards of the medical discipline tend to discourage such desires.

| I *really* just wanted to refute the idea that it was nuts to separate
| NIL and false.

  It _is_ nuts.  False is defined as nil.  Just as true is defined as t.

| For all the arguments in that direction, the obvious usability of Common
| Lisp means that it's also reasonable to conflate them, despite any
| conceptual messiness that might (or might not) entail.

  They are not conflated.  There is no conceptual messiness.  False is
  defined as nil.  True is defined as t.  That is how it is.  If you cannot
  deal with this, it is only your problem.  Augustine's prayer may apply:
  God grant me serenity to accept the things I cannot change, courage to
  change the things I can, and wisdom to know the difference.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwr8qqmwwg.fsf@shell01.TheWorld.com>
Bruce Hoult <·····@hoult.org> writes:

> In article <···············@shell01.TheWorld.com>, Kent M Pitman 
> <······@world.std.com> wrote:
> 
> > we have a 25-or-so year history
> > during which both Scheme and CL have existed, and in no cases have I
> > ever seen or heard of someone tearing out their hair and leaving the
> > CL community saying "I just can't build complex programs because this
> > NOT/NULL [or false/empty-list] thing is making it too hard to write
> > metaprograms".  It just doesn't happen.  So no one ever points to that
> > as the reason for splitting false/empty-list.  They point instead into
> > the murky depths of the human brain, citing simplicity without
> > defining their simplicity metric
> 
> Here's what I don't get about CL confusing false and the empty list:  
> suppose you have a function (foo name) that returns a list of all the 
> classes being taken by a student.  If the function returns NIL, does 
> that mean that the student is taking no classes at the moment, or does 
> it mean that the student doesn't exist?
> 
> It seems to me that *every* datatype deserves to potentially have a 
> "don't know" or "doesn't exist" value.  Like NULL in SQL.  An integer 
> field in a database can allow NULL, or can be declared to be NOT NULL 
> and this is an important distinction.  In any complex program some code 
> needs to be written to cope with NULL values, and some code wants to 
> assume that there is always valid data.
> 
> It's bad to use a value of zero in an integer variable to mean NULL.  
> It's bad to use a value of -1 in an integer variable to mean NULL.  It's 
> also bad, I think, to have a null pointer value in every pointer data 
> type.  How often do C programs fail because some function gets passed a 
> null pointer that didn't expect it?
> 
> It seems to me that using an empty list to represent NULL is just as bad.

I've said I don't have an opposition to more degenerate values.  But either
way, it's not a panacea.  You're basically saying that for every type FOO
there should be a type (NULL-OF FOO) which is a subtype of FOO and is useful
because it's not one of the ordinary examplars of FOO.  Well, first of all,
that's already not the empty list.  The empty list is not a non-list, it's
a list that's empty.  So the (NULL-OF LIST) would not be NULL but would be
a special non-list list, as opposed to an empty list.  Or, at least, I think
it should be.  You could probably make the case that the only "valid" lists
had elements, but I don't like that breakdown.  You could say it required
the (NULL-OF CONS) for this, and then there'd be discussion about whether
(NULL-OF CONS) could be car'd and cdr'd, since NIL can be, and maybe we'd say
yes, it is secretly a special cons with car and cdr of NIL.  But that all
sounds messy.  And what about programs that return type (or foo bar).  Is
there a type (NULL-OF (OR FOO BAR)) that is distinct from type (NULL-OF FOO)
and type (NULL-OF BAR)?  If so, it sounds like a mess to represent and 
recognize.  But ok, maybe.  I didn't think this through utterly but I feel
the phrase "set of all sets not contained in any set" is going to enter this
discussion really soon now...  I do know that every time there has been a
serious discussion of solving this, such a bubble really does creep in.  
No matter what set someone is returning, there's always a desire to squeeze
in just one extra element ... and often it defeats the whole point of having
picked the size of data storage one has chosen.  Just look at NUL-terminated
strings in C vs the ability to hold all 256 characters, or look at the 
opposite outcome in the utterly stupid Base64 MIME encoding, which requires 
65(!) characters to correctly represent it, so never really compacts up
quite right.
From: Harald Hanche-Olsen
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <pcon11esg4w.fsf@thoth.home>
+ Kent M Pitman <······@world.std.com>:

| No matter what set someone is returning, there's always a desire to squeeze
| in just one extra element ... and often it defeats the whole point of having
| picked the size of data storage one has chosen.  Just [...] look at the 
| opposite outcome in the utterly stupid Base64 MIME encoding, which requires 
| 65(!) characters to correctly represent it, so never really compacts up
| quite right.

I don't quite understand the relevance of this example, since the
purpose of using 64 characters for the Base64 encoding is not, I
believe, compactness of representation, but simplicity of coding and
decoding.  But it's true that the "=" padding character is not needed
for Base64 decoding: Just decode the input in groups of 4 characters
each producing 3 octets.  Then, when all these groups are used up, you
will be left with 0, 2 or 3 characters which decode into 0, 1 or 2
octets respectively.  So in this sense I can concur with your
characterization of Base64 as stupid.  But compared to the use of NUL
to terminate C strings it seems to me a minor stupidity indeed.

-- 
* Harald Hanche-Olsen     <URL:http://www.math.ntnu.no/~hanche/>
- Yes it works in practice - but does it work in theory?
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-E75035.15501723112001@news.paradise.net.nz>
In article <···············@shell01.TheWorld.com>, Kent M Pitman 
<······@world.std.com> wrote:

> I've said I don't have an opposition to more degenerate values.  But 
> either way, it's not a panacea.  You're basically saying that for
> every type FOO there should be a type (NULL-OF FOO) which is a subtype
> of FOO and is useful because it's not one of the ordinary examplars
> of FOO.

Close, but not quite.  I think it's more about bindings (and 
declarations of them as in, for example, CLOS method arguments) than 
about objects.  And CL as it is is very nearly what I'm talking about, 
with the single exception of the list type.

- you should be able to have a binding that you know has a valid value 
of the appropriate type

- you should be able to have a binding that might contain a valid value, 
or might contain the NULL value

- it's handy if the NULL value tests as false in conditional expressions

- I don't really care whether there is a different (NULL-OF FOO) for 
each type, but I'd suggest that it's fine to have them all be the same, 
e.g. #F.  More efficient to test for, too.


> Well, first of all, that's already not the empty list.  The empty list
> is not a non-list, it's a list that's empty.  So the (NULL-OF LIST)
> would not be NULL but would be a special non-list list, as opposed to
> an empty list.  Or, at least, I think it should be.

I agree.


> You could probably make the case that the only "valid" lists
> had elements, but I don't like that breakdown.

Sometimes that's useful, but not often.  The Dylan <list> class has two 
subclasses, <pair> and <empty-list>.  <empty-list> has a single 
instance, #().  So you can specialize a method on <list> and get either 
an empty or a non-empty list, or you can specialize on <pair> and get a 
guaranteed non-empty list.


> You could say it required the (NULL-OF CONS) for this, and then there'd
> be discussion about whether (NULL-OF CONS) could be car'd and cdr'd,
> since NIL can be, and maybe we'd say yes, it is secretly a special cons
> with car and cdr of NIL.  But that all sounds messy.

Very.  I'd think it should throw an exception.


> And what about programs that return type (or foo bar).  Is there a type
> (NULL-OF (OR FOO BAR)) that is distinct from type (NULL-OF FOO)
> and type (NULL-OF BAR)?  If so, it sounds like a mess to represent and 
> recognize.

I agree.  Easiest thing is to make (NULL-OF (OR FOO BAR)) be the same 
object as (NULL-OF FOO) and (NULL-OFF BAR).  I can't see any downside to 
this, and NIL already plays this role in CL.  That is to say, (NULL-OF 
(OR FOO BAR)) can be NIL and the return type of a function that might 
return a FOO or a BAR or NIL is (OR FOO BAR NULL).

This is all fine in CL already, *except* that a the list type is (OR 
CONS NULL) and (NULL-OF (OR CONS NULL)) is NIL, which is a valid list.  
That's why it would be better if there was a distinct "false" value 
which wasn't the same as an empty list.


> No matter what set someone is returning, there's always a desire
> to squeeze in just one extra element ... and often it defeats the
> whole point of having picked the size of data storage one has
> chosen.

Sure.  That's another good reason that you should be able to specify 
that some particular binding or slot CAN'T be NULL.

-- Bruce
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215481014063125@naggum.net>
* Bruce Hoult
| - I don't really care whether there is a different (NULL-OF FOO) for 
| each type, but I'd suggest that it's fine to have them all be the same, 
| e.g. #F.  More efficient to test for, too.

  The way you deal with these things for efficiency is to accept arguments
  of any complex (or ...) type you want, but then you something like this

(typecase <arg>
  (<type-1>
    (locally (declare (type <type-1> <arg>))
      ...))
  (<type-2
    (locally (declare (type <type-2> <arg>))
      ...)))

  This particular situation may actually be pre-optimized by your compiler
  with appropriate locally forms and declarations inserted for you.

| This is all fine in CL already, *except* that a the list type is (OR
| CONS NULL) and (NULL-OF (OR CONS NULL)) is NIL, which is a valid list.
| That's why it would be better if there was a distinct "false" value
| which wasn't the same as an empty list.

  "Better" in the absence of a context or a purpose renders the whole
  statement completely meaningless.  Most of the time, context-free
  "better" simply means "better for me, regardless of consequences or what
  other people need", and such statements should simply be ignored.  I
  would say they are arbitrary (which is even worse and more misleading
  than if they were false) because of the absence of specific meaning.

  I believe the only productive way to learn a new skill is to open one's
  mind to the superior knowledge of those who already know it well and
  really listen to their tales of what they went through to get where they
  are today.  If you come from somewhere else and have a different history
  behind you, whatever you come to will look strange, but if you think what
  you came from must always be more important than what you are going to,
  and some people mysteriously believe this _unconditionally_, it will be
  too hard for them to get into anything new, so they give up, and instead
  go on and on about how wrong what they came to is.  There are immigrants
  in every culture who keep longing for their past and denouncing their new
  living conditions for their entire life, but yet do not return.  I do not
  understand what is so special about what one accidentally met _first_
  that makes everything one meets later on _productively_ judged by it.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-869D0F.18521423112001@news.paradise.net.nz>
In article <················@naggum.net>, Erik Naggum <····@naggum.net> 
wrote:

> * Bruce Hoult
> | - I don't really care whether there is a different (NULL-OF FOO) for 
> | each type, but I'd suggest that it's fine to have them all be the same, 
> | e.g. #F.  More efficient to test for, too.
> 
>   The way you deal with these things for efficiency is to accept 
>   arguments
>   of any complex (or ...) type you want, but then you something like this
> 
> (typecase <arg>
>   (<type-1>
>     (locally (declare (type <type-1> <arg>))
>       ...))
>   (<type-2
>     (locally (declare (type <type-2> <arg>))
>       ...)))

That's right, except that you can't in CL distinguish between the empty 
list and false.

Everything else is fine.


>   I believe the only productive way to learn a new skill is to open one's
>   mind to the superior knowledge of those who already know it well and
>   really listen to their tales of what they went through to get where 
>   they are today.  If you come from somewhere else and have a different 
>   history behind you, whatever you come to will look strange, but if you
>   think what you came from must always be more important than what you
>   are going to, and some people mysteriously believe this
>   _unconditionally_, it will be too hard for them to get into anything
>   new, so they give up, and instead go on and on about how wrong what
>   they came to is.

That's a pretty much completely useless argument.  How are we then to 
distinguish me starting with Dylan and taking a look at CL from Erik 
Naggum starting with CL and taking a look at Dylan?  Are we doomed to 
always disagree?  I hope not.

Furthermore, it's not even a *correct* representation of the situation.  
I learned Lisp 1.5 long before I learned Dylan.  Contrary to your "baby 
duck syndrome" supposition, I saw that very many things in Dylan are 
done far better than in Lisp 1.5, separation of the concepts of false 
and empty list being just one of them.

And that's not even counting the various other journeys.  My first 
programming language was FORTRAN IV.  I saw that Pascal was bette, and 
moved to that, and then later saw that Modula-2 was better and moved to 
that.  Then I learned C and saw that it was better than Pascal but worse 
than Modula-2 and stayed with Modula-2.  Then C++ came along and I saw 
that it was better than Modula-2 and moved to it.  Then Java came along 
and I saw that it was worse than C++ + Boehm so I stayed with C++.  Oh, 
and I didn't mention the Data General machine I used in 1985 - 1986 
which had only FORTRAN, COBOL and PL/1 available and so I choose to use 
PL/1, that being the best of a bad lot.  Or probably another dozen or 
more languages along the way that I've learned, evaluated, and either 
used or discarded.

-- Bruce
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3BFDF255.3153E96F@nyc.rr.com>
Bruce Hoult wrote:
> 
> In article <················@naggum.net>, Erik Naggum <····@naggum.net>
> wrote:
.......
> >   I believe the only productive way to learn a new skill is to open one's
> >   mind to the superior knowledge of those who already know it well .....
> 
> That's a pretty much completely useless argument.  How are we then to
> distinguish me starting with Dylan and taking a look at CL from Erik
> Naggum starting with CL and taking a look at Dylan?  Are we doomed to
> always disagree?  I hope not.

You won't /always/ disagree because over time you get acquainted with
the different approach and your opinions will converge.

One of the things I sense about Lisp is that it has developed for a very
long time under the hands of folks who are insanely obsessed with doing
the Right Thing, and I think a large part of the determination of what
is the Right Thing comes from What Would A Reasonable Person Expect. And
so a Reasonable Person programs Lisp like a hot knife through warm
butter. But I digress.

A good example was my shift from MCL to ACL. My first reaction to ACL
was yechhh. But I figured it was just because I was used to MCL. Sure
enough, I now have no problems with ACL (and would probably have trouble
getting back into MCL).

So the point is, if you think the folks who created X gave it some
thought, take a few months to get into X before you dis it.

kenny
clinisys
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87u1vggt5i.fsf@teonanacatl.andreas.org>
Kenny Tilton <·······@nyc.rr.com> writes:

> One of the things I sense about Lisp is that it has developed for a very
> long time under the hands of folks who are insanely obsessed with doing
> the Right Thing, and I think a large part of the determination of what
> is the Right Thing comes from What Would A Reasonable Person Expect. And

I hoped that it would be like this.

But I'm seeing a lot of "Common Lisp does it that way and you need to
swallow it", and a lot of people who seem to have forgotten that
Common Lisp is man-made (and even designed by a committee and full of
bad compromises and legacy crap).

We folks from the Dylan community see ourselves as part of the Lisp
community.  That's not only because most of the Dylan designers were
also involved in the Common Lisp standardization process, but also
because the heritage shows in a lot of places, ranging from the object
system (modelled after CLOS), the optimzation theory (type
annotations), first class functions, to the UI framework (CLIM
vs. DUIM), the general compiler theory etc.  We're interested in an
honest discussion on what the Right Thing is (and yes, Dylan has it's
shortcomings too).

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215866242116385@naggum.net>
* Andreas Bogk
| But I'm seeing a lot of "Common Lisp does it that way and you need to
| swallow it", and a lot of people who seem to have forgotten that
| Common Lisp is man-made (and even designed by a committee and full of
| bad compromises and legacy crap).

  So are the laws of any given country.  You do not break them because you
  object to them, you enter politics and obey the laws while you change
  them.  If you are the fucking clueless moron who breaks laws you do not
  like, you are nothing but a retarded criminal.  Why the criminal mind is
  so important to hold up as a role model for social change is beyond me.

| We folks from the Dylan community see ourselves as part of the Lisp
| community.

  You seem to be quite alone in this regard, especially considering your
  hang to insult other Lisp communites and waltz in with stupid concerns
  that simply are _not_ concerns except to outsiders.  As convicted felons
  protest their innocence, but would not improve unless they accepted that
  they are guilty and the fate of the guilty, any random outsider who does
  not accept that complaining about non-issues is stupid or the negative
  consequences of such actions, will never be part of that community.

| We're interested in an honest discussion on what the Right Thing is (and
| yes, Dylan has it's shortcomings too).

  A good start would be to accept the choices people have made.  Coming
  into a new community and accusing people of regarding their standards as
  "gospel" because you want to be a criminal in that community is not a
  good start.  Strive not to be an outsider.  Do _not_ see yourself as an
  outsider.  (There are no "insiders", but people who choose to regard
  themselves as if they are always doomed to stand outside and look in,
  have no hope of ever gaining any useful information about what they keep
  looking at and not understanding.  Part of relinquishing the "outsider"
  status is to accept that other people have accepted certain things, and
  that they are _not_wrong_ in doing so even if you think it is not right.
  In time, you will see the wisdom that there are more than one right, that
  the idea that there is "one right" is wrong, but that this does not mean
  that one cannot determine that something will always be wrong no matter
  what is right.)

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87r8qkf32t.fsf@teonanacatl.andreas.org>
Erik Naggum <····@naggum.net> writes:

> | Common Lisp is man-made (and even designed by a committee and full of
> | bad compromises and legacy crap).
>   So are the laws of any given country.  You do not break them because you
>   object to them, you enter politics and obey the laws while you change
>   them.  If you are the fucking clueless moron who breaks laws you do not
>   like, you are nothing but a retarded criminal.  Why the criminal mind is
>   so important to hold up as a role model for social change is beyond me.

Gandhi made the concept of "civil disobedience" popular, and showed
that it works.

I do tend to break laws I consider immoral or meaningless.  Maybe this
has to do with the fact that I was raised in a dictatorship.

And changing a law works differently in practice: you throw a lot of
money at lobbyists.  I'm actively involved in fighting against new
surveillance laws, DMCA-like copyright regulations, and related civil
liberty issues.  Believe me, I know the mechanisms, and I'm depressed
at how the so-called democracies are run on this planet.

One of my research areas is cryptography, and I've been involved in
the GSM authentication attack and the DeCSS decryption software.  Laws
are on it's way that will outlaw this kind of research, driven by
nothing more than a handfull of intellectual property lawyers from the
recording and movie industry with an unlimited budget.

But this is starting to get severely off-topic, so I stop ranting
here.  For the purposes of this discussion, the summary is: I don't
buy that metaphor, please use another one.

> | We folks from the Dylan community see ourselves as part of the Lisp
> | community.
>   You seem to be quite alone in this regard, especially considering your
>   hang to insult other Lisp communites and waltz in with stupid concerns
>   that simply are _not_ concerns except to outsiders.  As convicted felons

And what way do you suppose people shall learn something deep about
CL, except by discussing their concerns with those who know?  That
way, you keep outsiders to be outsiders.

>   protest their innocence, but would not improve unless they accepted that
>   they are guilty and the fate of the guilty, any random outsider who does
>   not accept that complaining about non-issues is stupid or the negative
>   consequences of such actions, will never be part of that community.

Then consider yourself something like a secret conspiracy.

> | We're interested in an honest discussion on what the Right Thing is (and
> | yes, Dylan has it's shortcomings too).
>   A good start would be to accept the choices people have made.  Coming

I do accept the choices, but I want to understand the reasoning behind
it.  This allows me to make a better decision for myself.

Just delivering the results without sharing the insights is keeping
out people.

>   into a new community and accusing people of regarding their standards as
>   "gospel" because you want to be a criminal in that community is not a
>   good start.  Strive not to be an outsider.  Do _not_ see yourself as an

I reject the notion of the Lisp community being identical to the
Common Lisp community, and I especially reject the notion of CL being
used as a guide to define who's a criminal in the Lisp community.

I feel I have a lot of common ground with many people here, basic
things like believing that automatic memory management, dynamic
typing, general function dispatch and interactive development are good
ideas.

>   looking at and not understanding.  Part of relinquishing the "outsider"
>   status is to accept that other people have accepted certain things, and
>   that they are _not_wrong_ in doing so even if you think it is not right.

If I find a feature that strikes me as odd, there could be different
things going on:

1) It's indeed a bit odd, but people get used to it soon, so it won't
   be a problem, but losing it wouldn't hurt either.

2) It's a powerful feature I hadn't discovered before that leads me to
   new ways to express my ideas, and it's incredibly valuable.

3) I am the first one to notice how to do much better.

Number 3 probably happens twice a lifetime, and is infinitely
valuable.  But already being able to tell the difference between 1 and
2 is important to gain real understanding.

>   In time, you will see the wisdom that there are more than one right, that
>   the idea that there is "one right" is wrong, but that this does not mean
>   that one cannot determine that something will always be wrong no matter
>   what is right.)

I fail to see how something can always be wrong, when something can't
always be right.  Successful dialog depends on understanding the
common set of prerequisites, and trying to share the workload for
reaching new insights based on these prerequisites.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215912561196938@naggum.net>
* Andreas Bogk
| I do tend to break laws I consider immoral or meaningless.  Maybe this
| has to do with the fact that I was raised in a dictatorship.

  It probably explains why it remained a dictatorship for so long if that
  is what it did to its people's concept of obeying laws while _not_ trying
  to change them.  However, I have no sympathy for those who cannot get
  over their hardships when these hardships go away.  Barring actual mental
  illness, there is simply no excuse for a thinking person _not_ to change
  his mind when he world changes around him.  And in fact, Common Lisp is
  _not_ a dictatorship.  It is a voluntary standard, but if you purport to
  conform to it, you can conform to it and be an honest person, or you can
  fail to conform to it while you say you and be a manipulating liar.  It
  seems to me that suffering dictatorships tells people that it is _right_
  to manipulate and lie, because if you do not engage in these tactics, you
  suffer and die.  That frame of mind may take a lot of work to get out of,
  but it is worth it.

| For the purposes of this discussion, the summary is: I don't buy that
| metaphor, please use another one.

  Then I will consider you a criminal in our little society, one who is
  fighting "laws he consider immoral or meaningless" simply because he has
  failed to think things through.

| That way, you keep outsiders to be outsiders.

  Being an outsider is a personal, voluntary choice of attitude, it is not
  something that others can impose on you.

| Then consider yourself something like a secret conspiracy.

  Again, why do _you_ think in such terms?  _This_ is your core problem.

| Just delivering the results without sharing the insights is keeping out
| people.

  There is no such active purpose or intent.  You are not in an oppressive
  dictatorship, anymore.  Adjust accordingly.

| I reject the notion of the Lisp community being identical to the
| Common Lisp community, and I especially reject the notion of CL being
| used as a guide to define who's a criminal in the Lisp community.

  Of course you do.  You are a criminal in this community, and you want
  Dylan to be a Lisp.  This is no different from a Scheme freak who has
  made up his mind that Scheme is a Lisp, such that he can capitalize on
  the value of being a Lisp, but can still blame "Lisp" for shortcomings
  while keeping everything good to be associated with "Scheme".

| I feel I have a lot of common ground with many people here, basic things
| like believing that automatic memory management, dynamic typing, general
| function dispatch and interactive development are good ideas.

  Intelligent people tend to find people with whom they have common
  disagreements, not common agreements.  It is not what people think is
  right that unite smart people, it is what they think is wrong.  This is
  also what keeps reasonable societies and communities together.  Since you
  have experience with dictatorships, you may recognize that what makes a
  society a dictatorship is that its people are forced to agree on what is
  right, and that has _horrible_ results.

| If I find a feature that strikes me as odd, there could be different
| things going on:
| 
| 1) It's indeed a bit odd, but people get used to it soon, so it won't
|    be a problem, but losing it wouldn't hurt either.

  Getting rid of it would hurt all those who are already used to it.

* Erik Naggum
> In time, you will see the wisdom that there are more than one right, that
> the idea that there is "one right" is wrong, but that this does not mean
> that one cannot determine that something will always be wrong no matter
> what is right.

| I fail to see how something can always be wrong, when something can't
| always be right.

  That is because you warped the statement into meaninglessness.  Please
  think about it some more.  Many people spend _years_ coming to grips with
  this inequality of the determinability of right and wrong and of making
  the mistake of believing that _a_ right answer is _the_ right answer.
  Wars have been fought over this, and many lives lost in bad cultures.

  E.g., you can determine that something cannot be right concurrently with
  something else (that is right) because they exclude eachother completely.
  This is eminently possible without knowing what is _actually_ right.
  Most of how we build (good) societies is based on this principle.

  Some people tend to think that because they find evidence of something,
  they can conclude that they have that something.  This is false.  It is
  only if you do not find evidence of _not_ being something that you can
  say that.  Until you have looked for and not found counter-evidence,
  _you_ have contributed the conclusion from evidence that could point in
  any direction.  Remember, from a single data point, you can extrapolate
  in any direction.  Counterinformation is more important than information
  in determining what you have really found, because it helps exclude that
  which _could_ be right, but actually are not.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Ray Blaak
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <m3wv0b70mt.fsf@blight.transcend.org>
Erik Naggum <····@naggum.net> writes:
> | For the purposes of this discussion, the summary is: I don't buy that
> | metaphor, please use another one.
> 
>   Then I will consider you a criminal in our little society, one who is
>   fighting "laws he consider immoral or meaningless" simply because he has
>   failed to think things through.

So who are you? Judge, jury and jailer?

How could criticism of Lisp in general and CL in particular be possibly
considered criminal? That is ridiculous. Criticism and discussion is hardly the
violation of any "law".

The only possible crime that could occur in the context of CL is to implement a
language that does not conform to the standard and then call it Common
Lisp. There are no other "laws" that could be violated.

When debating the merits of a language, however, anything goes, especially in a
usenet group.

Ideally, smart people who disagree about important issues offer criticisms.
Rebuttals are returned. In the ensuing debate the various tradeoffs are
realized and understood, and everyone is that much wiser, even if their
positions are not necessarily changed.

> * Erik Naggum
> > In time, you will see the wisdom that there are more than one right, that
> > the idea that there is "one right" is wrong, but that this does not mean
> > that one cannot determine that something will always be wrong no matter
> > what is right.

Even if you determine to your satisfaction that something is always wrong,
smart people can still disagree with you. If they are indeed incorrect, the
resulting discussion ideally should still be rewardingly illuminating to
all. If you get bored with repeating the same old arguments, you can point
people to a FAQ, let someone else carry the "fight", or else simply ignore
them.

Andreas's real crime here seems to be 1) that he is into Dylan, 2) thinks it's
in the Lisp family, and 3) has the audacity to criticize your favourite
language.

Where *else* can he discuss Lisp's shortcomings in a meaningful manner? The
people who can most intelligently correct the error of his ways hang out here.

-- 
Cheers,                                        The Rhythm is around me,
                                               The Rhythm has control.
Ray Blaak                                      The Rhythm is inside me,
·····@telus.net                                The Rhythm has my soul.
From: Janis Dzerins
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <871yijjhvz.fsf@asaka.latnet.lv>
Ray Blaak <·····@telus.net> writes:

> Erik Naggum <····@naggum.net> writes:
> > | For the purposes of this discussion, the summary is: I don't buy that
> > | metaphor, please use another one.
> > 
> >   Then I will consider you a criminal in our little society, one who is
> >   fighting "laws he consider immoral or meaningless" simply because he has
> >   failed to think things through.
> 
> So who are you? Judge, jury and jailer?

Look at yourself.

> How could criticism of Lisp in general and CL in particular be
> possibly considered criminal? That is ridiculous. Criticism and
> discussion is hardly the violation of any "law".

Smart people (as you like to call them) are concerned only about
constructive criticism. Criticism of things one does not understand is
not a constructive criticism.

-- 
Janis Dzerins

  Eat shit -- billions of flies can't be wrong.
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215955227152621@naggum.net>
* Ray Blaak
| So who are you? Judge, jury and jailer?

  It is a metaphor, intended to show a particular attitude that has an
  exact parallel in the real world.  Grow a clue, now.

| Andreas's real crime here seems to be 1) that he is into Dylan, 2) thinks
| it's in the Lisp family, and 3) has the audacity to criticize your
| favourite language.

  Nonsense.  He speaks of what he does not know.  He also criticizes with
  no intention of resolving anything.  Common Lisp is not being designed at
  this time, and these things are so fundamental that there is no way his
  criticism can possibly stop, because they are not going to change.  There
  is no way this person is going to cease his complaints, because he will
  never be satisfied.  Why do you defend such people and activities?

| Where *else* can he discuss Lisp's shortcomings in a meaningful manner?
| The people who can most intelligently correct the error of his ways hang
| out here.

  No, the error of his ways is that he thinks that a newcomer to town
  should be _respected_ for disagreeing with the prevailing customs for no
  better reason than that they are different where he came from.  This is
  fantastically stupid in real life, too, and has a name: "an obnoxious
  tourist".  There is no confusion or error that anybody else can fix.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Ray Blaak
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <uwv0au6gy.fsf@telus.net>
Erik Naggum <····@naggum.net> writes:
> Why do you defend such people and activities?

I object only to his being called a criminal. The metaphor is not applicable
since there are no laws being violated. "Obnoxious tourist" would be much more
accurate, and while despicable, is not a crime in any part of the world that I
know of.

He is only talking for Christ's sake. Debunk him or ignore him.

-- 
Cheers,                                        The Rhythm is around me,
                                               The Rhythm has control.
Ray Blaak                                      The Rhythm is inside me,
·····@telus.net                                The Rhythm has my soul.
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215960502366628@naggum.net>
* Ray Blaak
| I object only to his being called a criminal. The metaphor is not applicable
| since there are no laws being violated.

  The metaphor does not concern _what_ one disregards, considers oneself
  above, disrespects, etc, but _that_ one knows better than the community
  and that if there is ever some disagreement, the community is wrong for
  making its choices.

| "Obnoxious tourist" would be much more accurate, and while despicable, is
| not a crime in any part of the world that I know of.

  Ok, so you have a personal hangup about "criminal" and only think it
  concerns "crime", and not the personal attitude towards authority.  I
  shall make a small note of this, and that you refuse to get the point.
  Fine with me.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <874rneditc.fsf@teonanacatl.andreas.org>
Erik Naggum <····@naggum.net> writes:

> | I do tend to break laws I consider immoral or meaningless.  Maybe this
> | has to do with the fact that I was raised in a dictatorship.
>   It probably explains why it remained a dictatorship for so long if that
>   is what it did to its people's concept of obeying laws while _not_ trying
>   to change them. 

The real reason has probably more to do with the fact that the limited
freedom resulted in a greatly improved personal and social security:
nobody was homeless or out of work, women's liberation was not just a
promise but fact, and the material difference between the rich and the
poor was almost inivisible by today's standards.

Have *you* ever tried to change a law?

>   his mind when he world changes around him.  And in fact, Common Lisp is
>   _not_ a dictatorship.  It is a voluntary standard, but if you purport to
>   conform to it, you can conform to it and be an honest person, or you can
>   fail to conform to it while you say you and be a manipulating liar.  It

You must confuse me with somebody else.  All I'm saying is that if I
fail to conform to Common Lisp, it is still Lisp.

>   Then I will consider you a criminal in our little society, one who is
>   fighting "laws he consider immoral or meaningless" simply because he has
>   failed to think things through.

Usually considering something immoral and meaningless involves thinking.

> | Then consider yourself something like a secret conspiracy.
>   Again, why do _you_ think in such terms?  _This_ is your core problem.

Because *you* treat me that way, and I suggest this is *your* problem.
Seems to be hard for you to understand.

> | Just delivering the results without sharing the insights is keeping out
> | people.
>   There is no such active purpose or intent.  You are not in an oppressive
>   dictatorship, anymore.  Adjust accordingly.

I am not suggesting purpose or intent, I'm observing effects.

>   Of course you do.  You are a criminal in this community, 

... by your dubious definition of criminal.

>   and you want Dylan to be a Lisp. 

Well, it is.  It's not Common Lisp, though.

>   This is no different from a Scheme freak who has
>   made up his mind that Scheme is a Lisp, such that he can capitalize on
>   the value of being a Lisp, but can still blame "Lisp" for shortcomings
>   while keeping everything good to be associated with "Scheme".

If he says Scheme is a Lisp, and that Lisp has shortcomings, he's
saying that Scheme has shortcomings.  So there's no point.

What I want to captialize on is sharing experience with other Lisp
people about the common foundations.  You can hardly blame me for
that.

> > In time, you will see the wisdom that there are more than one right, that
> > the idea that there is "one right" is wrong, but that this does not mean
> > that one cannot determine that something will always be wrong no matter
> > what is right.
> | I fail to see how something can always be wrong, when something can't
> | always be right.
>   That is because you warped the statement into meaninglessness.  Please

Could be that the statement was meaningless to begin with.

>   think about it some more.  Many people spend _years_ coming to grips with
>   this inequality of the determinability of right and wrong and of making
>   the mistake of believing that _a_ right answer is _the_ right answer.

I don't believe that *a* right answer is *the* right answer.  It's
hard to find out how you read that from my above comment.

It's just that I don't think that *a* wrong answer is *the* wrong
answer, for precisely the same reason.  That's what I have written
above, and it would suit you well to address this argument, instead of
handwaving.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215968035711923@naggum.net>
* Andreas Bogk
| Have *you* ever tried to change a law?

  Yes.  I also succeeded.  Next moronic question, please.

| All I'm saying is that if I fail to conform to Common Lisp, it is still
| Lisp.

  This is sheer idiocy.  Implying that you believe something so
  fantastically moronic is not a very smart move on your part.

> Then I will consider you a criminal in our little society, one who is
> fighting "laws he consider immoral or meaningless" simply because he has
> failed to think things through.

| Usually considering something immoral and meaningless involves thinking.

  A typical moron response.  "Fail to think things _through_" cannot be
  countered simply by arguing that something "usually involves thinking".
  In fact, you _support_ my argument that yo do not think things _through_.

| Because *you* treat me that way, and I suggest this is *your* problem.
| Seems to be hard for you to understand.

  When a criminal gets caught, it is always whoever catches him who is to
  blame for his predicament.  That you react this way supports my image of
  you as someone who has not learned to subordinate his desires to that of
  an authority.  Usually, this is due to massive immaturity or arrested
  development, but sometimes, it is a kind of arrogance that actually has
  concluded that society can go to hell.  How do you make people change
  their mind once you have given them this "impression"?  You _THINK_ and
  provide them with counter-evidence.  Of course, trying to give you any
  counter-evidence to your religious lunacy has made you even _more_
  certain that you are right.  This indicates that you retarded or have
  never actually _observed_ that you have been wrong at any time in your
  whole life.  This goes with the arrogance and maturity problems you have
  so far made a point out of underlining.

� If you do not like this "personal touch", quit accusing people of being
  religious simply because you are too stupid to argue against them.

> and you want Dylan to be a Lisp. 

| Well, it is.  It's not Common Lisp, though.

  Dylan is a Lisp the day Perl is a Lisp.  For the same reason.

| If he says Scheme is a Lisp, and that Lisp has shortcomings, he's saying
| that Scheme has shortcomings.  So there's no point.

  Sigh.  You probably even believe this.  I feel sorry for you the day when
  you figure out what marketing is made of, indeed human communication.

| What I want to captialize on is sharing experience with other Lisp people
| about the common foundations.  You can hardly blame me for that.

  I can blame you for not inviting people into your little pond to discuss
  them there, and that is what I do.  Go back to comp.lang.dylan and talk
  about your favorite Dylan things there.  Invite Lisp people to your forum.
  Obviously, you know that this will fail to have any desired impact, and
  still you have not figured out why Scheme people talk negatively about
  "Lisp" and positively about "Scheme".  Pretty amazing, really.

| I don't believe that *a* right answer is *the* right answer.  It's
| hard to find out how you read that from my above comment.

  Really?  A moron who finds evidence of religion at the drop of a hat has
  problems figuring out how his own arguments look to others.  Dude, how
  have you managed to stay alive so long?

| It's just that I don't think that *a* wrong answer is *the* wrong answer,
| for precisely the same reason.  That's what I have written above, and it
| would suit you well to address this argument, instead of handwaving.

  If _a_ wrong answer was _the_ wrong answer, it would mean that every
  _other_ answer would be right.  Such is the implication of "_the_ right
  answer", but I am not surprised that you do not get this.  I think I have
  had enough of your idiocy, now.  You clearly cannot think under pressure,
  much less logically, so I asusme that your brain actually only functions
  when your ego is massaged sufficiently, so it can only be used when you
  feel safe and secure.  That is pretty useless -- thinking hard should be
  most available because it is most _useful_ when you are under pressure.
  You are not even smart enough to hold back from posting until you can
  start to think clearly.

  Dylan seems to breed idiots faster than it breeds applications.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Lieven Marchand
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <m3oflonpbi.fsf@localhost.localdomain>
Andreas Bogk <·······@andreas.org> writes:

> But I'm seeing a lot of "Common Lisp does it that way and you need to
> swallow it", and a lot of people who seem to have forgotten that
> Common Lisp is man-made (and even designed by a committee and full of
> bad compromises and legacy crap).

I'm not sure where you see this, but perhaps I'm too close to it. One
argument that is less important to the Dylan community then to the CL
community is the cost of change. There is a larger amount of CL code
around, more CL books and tutorials and more CL implementations, so
any proposed change not only has to prove its use, but also its cost
effectiveness. For a lot of the minor things where people argue about,
changing them wouldn't be worth it even if you could convince
everyone.

Even perfect updates to the standard have a cost.  Consider the
changes between Ada 83 and Ada 95. There is a large consensus in the
Ada community that Ada 95 is a far better language then Ada 83. But
the real or perceived cost and difficulty of complying to the new
standard has made a number of commercial implementors decide to drop
their Ada offerings, which has caused problems where platforms no
longer had a commercially available Ada compiler.

-- 
Lieven Marchand <···@wyrd.be>
She says, "Honey, you're a Bastard of great proportion."
He says, "Darling, I plead guilty to that sin."
Cowboy Junkies -- A few simple words
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87elmkez7e.fsf@teonanacatl.andreas.org>
Lieven Marchand <···@wyrd.be> writes:

> I'm not sure where you see this, but perhaps I'm too close to it. One
> argument that is less important to the Dylan community then to the CL
> community is the cost of change. There is a larger amount of CL code
> around, more CL books and tutorials and more CL implementations, so
> any proposed change not only has to prove its use, but also its cost
> effectiveness. For a lot of the minor things where people argue about,
> changing them wouldn't be worth it even if you could convince
> everyone.

This is of course totally reasonable behaviour.  Nevertheless, there
might be people who don't have these constraints, or the cost might be
lower than people think.  So the discussion is not worthless.

Let me give you an example.  There seems to be a common consensus that
Emacs Lisp is broken.  However, the cost of change appears high:
there's lots of legacy code out there.

The biggest obstacle in automatic translation from elisp to, say,
scheme, is that elisp has dynamic scoping, whereas scheme (or CL for
that matter) employs lexical scoping.  Well, you could make all local
bindings dynamic bindings, but the code would be a mess.

On the ICFP2001 conference, there was a paper that described how to
employ data flow analysis to figure out which bindings could be
replaced by lexical bindings without changing the semantics of the
code.  A test with a representative file from Gnus showed that only 4
out of 150 bindings were actually used in a dynamic fashion.  These
can be refactored manually.

A scientific result changed what seemed to be like a heroic task into
something manageable.

It also works the other way around: the scientific community is always
looking for challenging problems of practical importance.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215920177087226@naggum.net>
* Andreas Bogk
| The biggest obstacle in automatic translation from elisp to, say,
| scheme, is that elisp has dynamic scoping, whereas scheme (or CL for
| that matter) employs lexical scoping.  Well, you could make all local
| bindings dynamic bindings, but the code would be a mess.

  Nonsense.  The biggest obstacle is that any usable Emacs would have to
  implement an Emacs Lisp so faithful to the original that it would never
  see any users switch to the new and improved Emacs Lisp who could find
  even a smidgeon of old Emacs Lisp code to get useful things done, and
  since the new Emacs would not supplant the old Emacs unless people were
  confident that their old Emacs Lisp stuff worked in the new, it would one
  giant project to prove that Emacs Lisp can be hosted on something other
  than the old C engine, which has approximately as much value to any Lisp
  community as a Dylan advocate wasting their time with design discussions.

  _People_ is the main impediment to human progress.  I wonder what kind of
  extraterrestial influences those who do not understand this are under.

| A scientific result changed what seemed to be like a heroic task into
| something manageable.

  I fear that you actually believe this, which is pretty tragic.
  
///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Tim Bradshaw
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <fbc0f5d1.0111281126.7c60847a@posting.google.com>
Andreas Bogk <·······@andreas.org> wrote in message news:<··············@teonanacatl.andreas.org>...
> Lieven Marchand <···@wyrd.be> writes:
> 
> > I'm not sure where you see this, but perhaps I'm too close to it. One
> > argument that is less important to the Dylan community then to the CL
> > community is the cost of change. There is a larger amount of CL code
> > around, more CL books and tutorials and more CL implementations, so
> > any proposed change not only has to prove its use, but also its cost
> > effectiveness. For a lot of the minor things where people argue about,
> > changing them wouldn't be worth it even if you could convince
> > everyone.
> 
> This is of course totally reasonable behaviour.  Nevertheless, there
> might be people who don't have these constraints, or the cost might be
> lower than people think.  So the discussion is not worthless.

It is worthless in the context of CL. There are clearly decisions that
CL made which are either fairly arbitrary (like NIL/false, perhaps) or
arguably wrong (some aspects of inheritance in CLOS).  The Lisp
community has already been through several sets of  such changes - the
changes involved in moving from pre-CL lisp systems to CL, and the
changes in moving from CLtL1 systems to ANSI CL systems.  I've been
involved in both of these (and I still occasionally have to fix CLtL1
issues in code), and I can tell you they are *bloody painful*, and
*bloody expensive*.

I don't pretend to speak for the Lisp community, but for myself I
don't ever want to have the language change out from under me in
incompatible ways again.  I have thousands and thousands of lines of
CL code which I use *all the time*, and I want to get on and live my
life and not ever have to worry about whether I've made some
possibly-now-invalid assumption in code I wrote at 4am, barely
understood at the time and definitely do not understand now.  There is
simply nothing that is wrong enough with CL that I want, ever, to see
incompatible changes. And the amount of code I use is pretty small by
many standards.

You have to remember that many people have been through this process,
moving code from MACLISP to Zetalisp to CL to ANSI CL or from
InterLisp to CL to ANSI CL, and doing it all over again just is not
attractive *especially* when the kinds of changes people are
suggesting are fixes to things that many do not regard as broken in
the first place.  There was a compelling reason to move things to CL,
there really is no compelling reason to make random small incompatible
tweaks to the language now.

It's like the side of the road you drive on: I mean it's just obvious
that driving on the wrong side is this stupid, dangerous idea.  It's
not like there's disagreement like there is with NIL/false - everyone
knows driving on the left is just *better*.  But it's really an
incompatible change, and it would be quite expensive to make, so it's
not generally considered worth it.  Indeed people who spend a lot of
time worrying about it are generally regarded in the driving community
as fools, especially when they insist on posting in
comp.driving.right.

Another thing people don't want to happen is fragmentation, and again,
that's because people have *seen* this happen before and they don't
want it to happen again.  CL was this heroic, hugely expensive (how
many millions of dollars I wonder? less than 1000?) effort to unite a
fragmented community which ultimately succeeded but in the process
just destroyed great areas of stuff. What happened to all the
InterLisp stuff? - it's all largely just vanished, because porting it
to CL was too hard.  I'm really too young to remember this, but I was
there when the InterLisp machines were going away and it was painful
to see how much stuff got lost, even in one fairly small project.  I
*still* don't have some of the tools I had then.  And, althogh you are
probably too young, a lot of people remember the bad taste left by
Dylan, which was seen as an attempt to fragment the community for no
very good reason: that was really a nasty experience.  So people don't
react too well to suggestions that involve incompatible new dialects,
and it's not really surprising.  And especially they do not react well
to suggestions of incompatible dialects based on something that many
people do not see as broken.
 
> On the ICFP2001 conference, there was a paper that described how to
> employ data flow analysis to figure out which bindings could be
> replaced by lexical bindings without changing the semantics of the
> code.  A test with a representative file from Gnus showed that only 4
> out of 150 bindings were actually used in a dynamic fashion.  These
> can be refactored manually.
> 
> A scientific result changed what seemed to be like a heroic task into
> something manageable.

I'm sorry, this is just laughable - this is everything which is wrong
about this kind of argument.  They loooked at *one file*!  Well, I
have maybe 100 files of random personal elisp code, lots of it written
in a real hurry and/or hacked from other stuff which I barely
understood. Lots of this stuff is probably marginal, already, but I
use it all the time.  There are nearly 1600 files, and a million
lines, of elisp in the xemacs distribution, *many* of which I use.  I
rely on this stuff *completely*  and if someone suggests that I should
fix my code because they want to change the way scoping works in elisp
then I'll stop upgrading.  Sure scoping in elisp is broken, but it's
just *not broken enough* that it is worth fixing.  I already find it
*significantly* painful to do emacs upgrades, and a change like this
is just not worth it.  I have better things to do with my time than
worry about incompatible changes to something like this.  It's not
like there's a performance problem or anything any more.

Here's another example: SunOS 4 to 5.  Again, you may not remember
what this was like, but many do (especially a lot of people at Sun I
bet).  SunOS 4 was really a mess, 4.0 was hopeless at the user level,
4.1 was kind of OK for users but internally horrible (there were,
seriously, things in the kernel like `x=x;' with a comment saying
`this makes it work').  SPARC support was wedged into it, and there
was basically no real chance of getting decent multiprocessor
performance because the architecture was so broken.  And lots of
commerical people wanted SysV, so there was hacked-in SysV stuff both
at user and kernel level.  It must have been horrible for Sun.  But
SunOS 5 took *years* to be accepted, because lots of people had all
sorts of stuff which really depended on SunOS 4 and *really* did not
want to change things, because from the user level 4.1.3 / 4.1.4
worked really OK, and early SunOS 5 was buggy and slow. I remember the
horror when Sun came out with machines (ultras? or was it before that)
which *would not run* SunOS 4, and the relief when we found that you
could, in fact, get SunOS 4 for them if you asked the right people. 
This must have cost Sun *enormous* amounts of money.  You can see how
bad it was by the fact that they've now renumbered things so no one
ever worries that there might be a SunOS 6 some day.  And that was a
change which - even though I'm a BSD person and it hurts to say this -
needed to be made.

Finally, the question is *why*?  Why are people obessing away about
NIL/false or other incompatible changes which have little benefit and
much cost, when instead you could be working in *compatible
enhancements*, which would have little cost and huge benefit.  I mean
there must be *millions* of things you could add to CL which would not
break a single line of existing conforming CL code and would provide
cool new stuff.  Tie down the MOP, for instance.  Design and get
agreement on a MP interface.  URIs.  Standard sockets.  FFI. 
Defsystem.  I can just keep typing these things in for ever.  *Why*
are you worrying about some trivial little design issue when you could
be doing something cool and new?  Come on, get *over* it, this is just
*STUPID*.

--tim
From: Brian Palmer
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <0whoflms0i4.fsf@elaine0.Stanford.EDU>
··········@tfeb.org (Tim Bradshaw) writes:

> It's like the side of the road you drive on: I mean it's just obvious
> that driving on the wrong side is this stupid, dangerous idea.  It's
> not like there's disagreement like there is with NIL/false - everyone
> knows driving on the left is just *better*.  But it's really an
> incompatible change, and it would be quite expensive to make, so it's
> not generally considered worth it.  Indeed people who spend a lot of
> time worrying about it are generally regarded in the driving community
> as fools, especially when they insist on posting in
> comp.driving.right.

? I'm not familiar with this argument. 
 
> *still* don't have some of the tools I had then.  And, althogh you are
> probably too young, a lot of people remember the bad taste left by
> Dylan, which was seen as an attempt to fragment the community for no
> very good reason: that was really a nasty experience.  So people don't
> react too well to suggestions that involve incompatible new dialects,
> and it's not really surprising.  And especially they do not react well
> to suggestions of incompatible dialects based on something that many
> people do not see as broken.

Right. That may explain things, but it doesn't entirely justify
matters. My perspective, as someone just starting out and learning
lisp (in particular, emacslisp more than common lisp), and who has
been lurking in the group for less than a year, is that the "Common
Lisp community" as represented on the newsgroup is very brittle. The
progression of some discussions have definitely left a very bad taste
in my mouth, even as uninvolved as I am in the group.

-- 
Brian Palmer
"Whoever fights monsters should see to it that in the process he does
not become a monster. And when you look long into an abyss, the abyss
also looks into you"  - Nietzsche
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3216002118211980@naggum.net>
* Brian Palmer
| My perspective [...] is that the "Common Lisp community" as represented
| on the newsgroup is very brittle. The progression of some discussions
| have definitely left a very bad taste in my mouth, even as uninvolved as
| I am in the group.

  It is indeed the case that the community is brittle.  We suffer morons
  from other communities all the time, we have traitors in our own camp,
  and we have "popularity problems" and all sorts of irrelevant issues that
  people who need an excuse _not_ to use (Common) Lisp need to feel good
  about themselves instead of feeling like idiots who do not just go and do
  what they want to do.  There have been such people in this newsgroup for
  the past 5 years at least.  I have argued that this dissatisfaction with
  a great language is actually causing all the lack of popularity, because
  whoever wants to do something great for a bunch of sourpusses who will
  whine and bitch about trivial idiotic things because they have a mental
  problem accepting the authority of the standard, or generally just have
  so big egos that they cannot deal with the rejection of their bad ideas?

  This is just like some refugees from lands of poverty and war and famine
  and pain and illness who spend their entire lives cursing the country
  that has given them everything, but never "enough", mainly because they
  have no idea how to go about getting what they want on their own.  There
  are some people who think the universe _owes_ them something.  For some
  reason, these people tend to come to Common Lisp, most probably because
  Common Lisp has also given people so much for free that they could never
  create on their own that they feel helpless if they need something they
  have not got.  Common Lisp is also kind of a _relief_ from all the
  moronic languages out there, and finding that the relief was not perfect
  may cause some people to feel a little betrayed and to want more for free.
  We see this in people who whine endlessly about various things that are
  not in the standard, so they cannot use whatever their implementation
  offers them.  Similarly nutty arguments are extremely exhausting.

  I have also argued that any random luser off the Net (it used to be the
  street, but the lusers are too fat to walk these days) can find something
  to improve on in any of those new toy languages, while it almost takes a
  genius to make _actual_ improvements to Common Lisp.  This means that
  among the million idiot ideas that get implemented and discussed in the
  new toy languages, one or two good ideas may survive the "masses", while
  we need about one good idea for every five failing ones in Common Lisp.

  In most other language communities, having your ideas rejected is no big
  deal, because you can come up with another one at little extra cost, but
  if you spent a year designing something super-clever that you really like
  and which you have used for a long time seeing it trashed viciously
  (because you refuse to back down and get increasingly hostile to those
  who simply did not like your idea to begin with) may be too much for some
  brittle egos.  However, as every successful person knows, you have to
  learn from but otherwise forget your failures -- harbor no regrets, just
  do better next time.  Several contributors to the Common Lisp community
  have actually expressed extreme hostility to the failure to accept their
  undoubtedly brilliant ideas in some other universe, but while the Scheme
  community encourages people to go off and implement their _own_ Scheme,
  the Common Lisp standard is so big and mature that those who want to
  reinvent the wheel, or at least a portion of the wheel (like an Arc :),
  usually fail miserably.  (Just look at Guile, an attempt to approach
  Common Lisp asymptotically, but which took off with just short of the
  escape velocity of Scheme.)  In short, there is much more self-screening
  and "perfectionism" in the Common Lisp community than other communities.

  What this is driving at is the unprofessionalism of the "lone programmer"
  -- and Lisp is so powerful that it does not _need_ large teams -- who
  very unfortunately takes his software development _personally_.  People
  fall in love with (Common) Lisp in strange ways and few seem to have that
  important ability to get up and walk away from their creations, to throw
  it away if it turns out to have outlived its usefulness, etc.  This hang
  to get personal about their profession is tremendously annoying, because
  it creates another barrier to acceptance of good ideas: the inability to
  reject someone's ideas without their feeling personally offended.  We
  also have some amazing nutballs in this forum who post for no other
  reason than to "exact some measure of revenge" (to quote at least one
  mass-murdering anti-government nationalist) against whoever they think is
  responsible for their rejection.   This _unprofessionalism_ is dangerous.

  What would help make the community less brittle?  Professional detachment
  from one's professional opinions.  Fewer people who take comments about
  their professional opinions personally.  Fewer people who post personal
  opinions in the guise of professional opinions.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Lieven Marchand
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <m3667utyzy.fsf@localhost.localdomain>
··········@tfeb.org (Tim Bradshaw) writes:

[ lots of stuff I agree with. These are a few snippings ]

> Sure scoping in elisp is broken, but it's just *not broken enough*
> that it is worth fixing.

If I could get magically one thing done to the elisp interpreter, it
wouldn't be scoping, it would be threading. I don't mind the dialect
all that much since I don't write in it all that much. But that when
gnus has a spot of network trouble it causes all other frames to go
blank is painful.

> Here's another example: SunOS 4 to 5.  Again, you may not remember
> what this was like, but many do (especially a lot of people at Sun I
> bet).  

Ask Larry McVoy about it. He left Sun and hasn't gotten over it yet.

> Finally, the question is *why*?  Why are people obessing away about
> NIL/false or other incompatible changes which have little benefit and
> much cost, when instead you could be working in *compatible
> enhancements*, which would have little cost and huge benefit.  I mean
> there must be *millions* of things you could add to CL which would not
> break a single line of existing conforming CL code and would provide
> cool new stuff.  Tie down the MOP, for instance.  Design and get
> agreement on a MP interface.  URIs.  Standard sockets.  FFI. 
> Defsystem.  I can just keep typing these things in for ever.  *Why*
> are you worrying about some trivial little design issue when you could
> be doing something cool and new?  Come on, get *over* it, this is just
> *STUPID*.

Amen.

-- 
Lieven Marchand <···@wyrd.be>
She says, "Honey, you're a Bastard of great proportion."
He says, "Darling, I plead guilty to that sin."
Cowboy Junkies -- A few simple words
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215997328977784@naggum.net>
* Tim Bradshaw
| Here's another example: SunOS 4 to 5.  [...]  It must have been horrible
| for Sun.  But SunOS 5 took *years* to be accepted, because lots of people
| had all sorts of stuff which really depended on SunOS 4 and *really* did
| not want to change things, because from the user level 4.1.3 / 4.1.4
| worked really OK, and early SunOS 5 was buggy and slow.

  While we are telling stories: Some bigwhig from Sun made a bet at a
  conference that there would be no more SunOS 4 versions after 4.1.3.
  Then a new version came out, so he lost his bet.  Lots of people never
  figured out the joke in its version designation, so allow me to repeat
  this even though lots of people _did_ get it.  It was called 4.1.3_U1.
  Get it?  (Pronounce it.  Get it now?  :)

| Finally, the question is *why*?  [...]  I mean there must be *millions*
| of things you could add to CL which would not break a single line of
| existing conforming CL code and would provide cool new stuff.  Tie down
| the MOP, for instance.  Design and get agreement on a MP interface.
| URIs.  Standard sockets.  FFI.  Defsystem.  I can just keep typing these
| things in for ever.  *Why* are you worrying about some trivial little
| design issue when you could be doing something cool and new?  Come on,
| get *over* it, this is just *STUPID*.

  Because it is the only contribution these feebleminded morons can make.
  It is based on some theoretical foundation that is just plain _wrong_,
  and that means it violates an artificial "pattern of design" that some
  people are so unbelievably anal about adherence to that they simply go
  nuts if somebody does something else.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Tim Bradshaw
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <fbc0f5d1.0111290343.6d255f9e@posting.google.com>
Erik Naggum <····@naggum.net> wrote in message news:<················@naggum.net>...
>   While we are telling stories: Some bigwhig from Sun made a bet at a
>   conference that there would be no more SunOS 4 versions after 4.1.3.
>   Then a new version came out, so he lost his bet.  Lots of people never
>   figured out the joke in its version designation, so allow me to repeat
>   this even though lots of people _did_ get it.  It was called 4.1.3_U1.
>   Get it?  (Pronounce it.  Get it now?  :)

(:-). Wasn't there a 4.1.4 later on?  I forget.  Anyway the thing I
heard was that weird things happened with numbering (kind of akin to
the 5.6/7 saga, but mure amusing I think) about 4.1.  Some post 4.1
release - maybe 4.1.3 but I'm not sure - suffered a change where
essentially everything got shunted down a level, so it really was a
single-dot release not a double-dot release.  In fact it was really
4.2, but Sun didn't want to call their OS <anything>-4.2 because of a
certain historically significant Unix version...

--tim
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-BDED06.11560129112001@news.paradise.net.nz>
In article <····························@posting.google.com>, 
··········@tfeb.org (Tim Bradshaw) wrote:

> I don't pretend to speak for the Lisp community, but for myself I
> don't ever want to have the language change out from under me in
> incompatible ways again.  I have thousands and thousands of lines of
> CL code which I use *all the time*, and I want to get on and live my
> life and not ever have to worry about whether I've made some
> possibly-now-invalid assumption in code I wrote at 4am, barely
> understood at the time and definitely do not understand now.  There is
> simply nothing that is wrong enough with CL that I want, ever, to see
> incompatible changes. And the amount of code I use is pretty small by
> many standards.

So *this* is where all the defensiveness here is coming from!!

Every time I or Andreas or someone else is interested in learning about 
and comparing the way CL does something with the way that other 
langauges do similar things, you for some reason I don't fathom 
immediately think that they want to *change* CL.

Quite apart from being false, it is a preposterous idea to imagine that 
I have the *power* to bend the CL standard to my will even if for some 
strange reason I *wanted* to.  I would never have thought of it as a 
possibility.  I'm astounded that you seem to think it's a possiblity.

Astounded.

-- Bruce
From: Jochen Schmidt
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <9u4051$h1j$1@rznews2.rrze.uni-erlangen.de>
Bruce Hoult wrote:

> In article <····························@posting.google.com>,
> ··········@tfeb.org (Tim Bradshaw) wrote:
> 
>> I don't pretend to speak for the Lisp community, but for myself I
>> don't ever want to have the language change out from under me in
>> incompatible ways again.  I have thousands and thousands of lines of
>> CL code which I use *all the time*, and I want to get on and live my
>> life and not ever have to worry about whether I've made some
>> possibly-now-invalid assumption in code I wrote at 4am, barely
>> understood at the time and definitely do not understand now.  There is
>> simply nothing that is wrong enough with CL that I want, ever, to see
>> incompatible changes. And the amount of code I use is pretty small by
>> many standards.
> 
> So *this* is where all the defensiveness here is coming from!!

huh?
 
> Every time I or Andreas or someone else is interested in learning about
> and comparing the way CL does something with the way that other
> langauges do similar things, you for some reason I don't fathom
> immediately think that they want to *change* CL.

No - the annoying fact is that the way you both argue shows that you are 
not interested in finding what could be done better in Dylan but more 
finding arguments were CL is worse than Dylan.

You came here and proclaimed that CL seems to have a problem because it does
not distinguish nil/false/'() and Dylan has done this better. You then *got*
your answer that no lisper here ever had any problem with this issue and 
that it is even counted as a feature in some contexts. But instead of 
learning from that, you annoy people by insisting that lispers should have 
a problem if they think so or not only because you think it fits your bill 
and CL is wrong and Dylan is right completely forgetting the fact that only 
the community itself is able what is counted right or wrong.

You criticize that this facility is restricted to lists while Dylan has all 
this generic container stuff - completely forgeting the fact that lists are 
of *much* higher value in a language that got not crippled by omitting 
s-expressions.

One thing you both seem to completely forget is that your silly little 
language-war is really a disservice to Dylan. Many lispers may try out 
Dylan from themselves but if they get insulted and annoyed by some language 
fanatics I think the chance for that is quickly decreasing against zero.
(This is at least the effect this discussions had to me so far...)

Jochen Schmidt

--
http://www.dataheaven.de
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-26B12F.15440329112001@news.paradise.net.nz>
In article <············@rznews2.rrze.uni-erlangen.de>, Jochen Schmidt 
<···@dataheaven.de> wrote:

> No - the annoying fact is that the way you both argue shows that you are 
> not interested in finding what could be done better in Dylan but more 
> finding arguments were CL is worse than Dylan.

If that is the impression you get then it is an incorrect one.

 
> You came here and proclaimed that CL seems to have a problem
> because it does not distinguish nil/false/'() and Dylan has done
> this better.

That is factually incorrect.

Thomas F. Burdick made that claim, purely about CL with no reference to 
Dylan, in <···············@conquest.OCF.Berkeley.EDU>.  I later came 
into the thread to offer my experiences and thoughts.


> One thing you both seem to completely forget is that your silly little 
> language-war is really a disservice to Dylan.

There is no language war from my side.  I think both CL and Dylan are 
valuable languages to have in your toolkit, and I would welcome the 
chance to work professionally in either.


> Many lispers may try out Dylan from themselves but if they get
> insulted and annoyed by some language fanatics I think the chance
> for that is quickly decreasing against zero.

CL of course has no language fanatics.

-- Bruce
From: Jochen Schmidt
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <9u648q$gcr$1@rznews2.rrze.uni-erlangen.de>
Bruce Hoult wrote:

> In article <············@rznews2.rrze.uni-erlangen.de>, Jochen Schmidt
> <···@dataheaven.de> wrote:
> 
>> No - the annoying fact is that the way you both argue shows that you are
>> not interested in finding what could be done better in Dylan but more
>> finding arguments were CL is worse than Dylan.
> 
> If that is the impression you get then it is an incorrect one.

Some smart guy told me one day that what gets communicated is not what one
says but what the other side understands. So if you want to transmit 
information it is _your_ responsibility to make clear what you mean - not 
mine.

>> You came here and proclaimed that CL seems to have a problem
>> because it does not distinguish nil/false/'() and Dylan has done
>> this better.
> 
> That is factually incorrect.
> 
> Thomas F. Burdick made thatkdi claim, purely about CL with no reference to
> Dylan, in <···············@conquest.OCF.Berkeley.EDU>.  I later came
> into the thread to offer my experiences and thoughts.

No it is not factually incorrect. I said that you "proclaimed that CL seems 
to have a problem...". This does not imply that you was the one who started 
this discussion.

>> One thing you both seem to completely forget is that your silly little
>> language-war is really a disservice to Dylan.
> 
> There is no language war from my side.  I think both CL and Dylan are
> valuable languages to have in your toolkit, and I would welcome the
> chance to work professionally in either.

Then I still cannot understand why you have to insist on the claim that CL 
is wrong and Dylan is right completely ignoring any comments from people 
that actually _use_ CL.
What is holding you off opening your little book of Dylan-lacks and write 
into it 

  "- nil/false/'() issue no problem for either Dylan or CL" 

and be satisfied that neither CL nor Dylan has to be changed to be right in 
each others way.

>> Many lispers may try out Dylan from themselves but if they get
>> insulted and annoyed by some language fanatics I think the chance
>> for that is quickly decreasing against zero.
> 
> CL of course has no language fanatics.

Why do you try reading between the lines when there is nothing there?
In my experience every community of significant size has fanatics.
It is simply wrong to draw from that the conclusion that it is ok to behave 
like a language fanatic.

ciao,
Jochen

--
http://www.dataheaven.de
From: Tim Bradshaw
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <fbc0f5d1.0111290308.55d0a1e5@posting.google.com>
Bruce Hoult <·····@hoult.org> wrote in message news:<···························@news.paradise.net.nz>...
> 
> Every time I or Andreas or someone else is interested in learning about 
> and comparing the way CL does something with the way that other 
> langauges do similar things, you for some reason I don't fathom 
> immediately think that they want to *change* CL.

No, I don't think that.  Obviously I've either expressed myself badly
or you are not undertanding what I'm trying to say.

What I'm trying to say is that whether NIL and false are different is
this *tiny bit of linguistic trivia* which it is a *complete waste of
time* to discuss.  I don't know if Dylan or Scheme are `better' than
CL, or if Java is `better' than C++, but if they are it absolutely *is
not* to do with whether they equate NIL, or 0, with falsehood.  There
are much bigger issues here.

And further, what I'm trying to say is that it *might* have been
interesting to discuss NIL/false when this part of the language was
being designed, but now it's done it is not interesting any more
because that stage of design is all done now.

It seems to be a fairly common tendency to stress away about these
trivial issues in cll (and elsewhere, I guess), and it's just a huge
waste of time.  As far as I can see it's partly to do with people who
haven't been able to get over losing what they saw as some battle, and
obsess endlessly about it, and it's partly to do with being a
convenient way of not thinking about actual real problems.  Finally
it's a classic cult thing - since no change can happen it's safe to
discuss how things would be different/better if the change did happen.

I think we need to stop looking backwards and re-fighting old battles,
won or lost, and look at the future.  We can't change the past, all
that stuff is sunk cost now.  If we have to look backwards, we should
look at *important* bits of history, not trivial ones, even though
it's easier to look at the trivial ones.  An important bit of history
might be `why did Symbolics lose to Sun?'  If the answer has anything
to do with Lisp at all, it *certainly* does not have to do with
NIL/false, inheritance issues, or even Lisp1/Lispn for that matter:
those things are just in the noise, even though they are much easier
to have opinions about than the real issues.

We need to be forward-looking, and discussing unchangable linguistic
trivia is not forward-looking, even though it may be more confortable
for many.

--tim
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87r8qha4h7.fsf@teonanacatl.andreas.org>
··········@tfeb.org (Tim Bradshaw) writes:

> What I'm trying to say is that whether NIL and false are different is
> this *tiny bit of linguistic trivia* which it is a *complete waste of
> time* to discuss. 

Is it a complete waste of time for a teacher to teach, because he
already knows what he's teaching?

If it is a complete waste of time for you, don't discuss.

*I* have learned a lot during the discussion, and most points have
been made.  Thanks to the polite and smart people in this newsgroup
who are actually interested in teaching what they know.

> And further, what I'm trying to say is that it *might* have been
> interesting to discuss NIL/false when this part of the language was
> being designed, but now it's done it is not interesting any more
> because that stage of design is all done now.

Please understand that we are trying to gain a deeper insight.  We're
not just users of CL who need to get a job done, so we need not only
to understand what results from CL, but also what led to CL.

> that stuff is sunk cost now.  If we have to look backwards, we should
> look at *important* bits of history, not trivial ones, even though
> it's easier to look at the trivial ones.  An important bit of history
> might be `why did Symbolics lose to Sun?'  If the answer has anything

That's an interesting one.  I did some reading ("UNIX-HATERS
Handbook", "The Architecture of Symbolic Computing"), and their
explanations are:

- SUNs were cheaper
- SUNs were faster
- SUNs booted faster (although that one's probably tongue-in-cheek)
- Advance in compiler technology made special-purpose hardware superfluous
- Students were brainwashed at universities

The price tag is probably reason #1.  OpenGenera is still $5000 (if
anybody of you has a license of OpenGenera lying around that he could
lend, donate or sell cheaply to a student of Lisp and its history,
I'd be very happy).

> We need to be forward-looking, and discussing unchangable linguistic
> trivia is not forward-looking, even though it may be more confortable
> for many.

"Unchangable" depends on the point of view.  I completely understand
people's constraints, but they do not apply to all people.  And
discussing trivia has the potential to increase understanding, which
is what we are seeking.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Brian P Templeton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87heqjx8jn.fsf@tunes.org>
Andreas Bogk <·······@andreas.org> writes:

[...]
> The price tag is probably reason #1.  OpenGenera is still $5000 (if
> anybody of you has a license of OpenGenera lying around that he could
> lend, donate or sell cheaply to a student of Lisp and its history,
> I'd be very happy).
> 
You can get a LispM for $600 from Symbolics, IIRC.

[...]

-- 
BPT <···@tunes.org>	    		/"\ ASCII Ribbon Campaign
backronym for Linux:			\ / No HTML or RTF in mail
	Linux Is Not Unix			 X  No MS-Word in mail
Meme plague ;)   --------->		/ \ Respect Open Standards
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <871yhm90ro.fsf@teonanacatl.andreas.org>
Brian P Templeton <···@tunes.org> writes:

> > The price tag is probably reason #1.  OpenGenera is still $5000 (if
> > anybody of you has a license of OpenGenera lying around that he could
> > lend, donate or sell cheaply to a student of Lisp and its history,
> > I'd be very happy).
> You can get a LispM for $600 from Symbolics, IIRC.

That's the price for a MacIvory II, right.  I'll probably buy one of
these once my Paypal account is active.  I just hoped to get away
cheaper than that (a friend of mine has an old Alpha he's not using,
and it's got *way* more RAM than the MacIvory).

Anyways, for any serious work, one would want to run Open Genera on a
modern Alpha.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Brian P Templeton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <871yh8krgm.fsf@tunes.org>
Andreas Bogk <·······@andreas.org> writes:

> Brian P Templeton <···@tunes.org> writes:
> 
>> > The price tag is probably reason #1.  OpenGenera is still $5000 (if
>> > anybody of you has a license of OpenGenera lying around that he could
>> > lend, donate or sell cheaply to a student of Lisp and its history,
>> > I'd be very happy).
>> You can get a LispM for $600 from Symbolics, IIRC.
> 
> That's the price for a MacIvory II, right.  I'll probably buy one of
> these once my Paypal account is active.  I just hoped to get away
> cheaper than that (a friend of mine has an old Alpha he's not using,
> and it's got *way* more RAM than the MacIvory).
> 
Are you sure? IIRC, that's the price for a Symbolics 3600 LispM.

> Anyways, for any serious work, one would want to run Open Genera on a
> modern Alpha.
> 
> Andreas
> 
> -- 
> "In my eyes it is never a crime to steal knowledge. It is a good
> theft. The pirate of knowledge is a good pirate."
>                                                        (Michel Serres)

-- 
BPT <···@tunes.org>	    		/"\ ASCII Ribbon Campaign
backronym for Linux:			\ / No HTML or RTF in mail
	Linux Is Not Unix			 X  No MS-Word in mail
Meme plague ;)   --------->		/ \ Respect Open Standards
From: Raymond Wiker
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <864rm2lev9.fsf@raw.grenland.fast.no>
Brian P Templeton <···@tunes.org> writes:

> Andreas Bogk <·······@andreas.org> writes:
> 
> > Brian P Templeton <···@tunes.org> writes:
> > 
> >> > The price tag is probably reason #1.  OpenGenera is still $5000 (if
> >> > anybody of you has a license of OpenGenera lying around that he could
> >> > lend, donate or sell cheaply to a student of Lisp and its history,
> >> > I'd be very happy).
> >> You can get a LispM for $600 from Symbolics, IIRC.
> > 
> > That's the price for a MacIvory II, right.  I'll probably buy one of
> > these once my Paypal account is active.  I just hoped to get away
> > cheaper than that (a friend of mine has an old Alpha he's not using,
> > and it's got *way* more RAM than the MacIvory).
> > 
> Are you sure? IIRC, that's the price for a Symbolics 3600 LispM.

        It's also the price of a MacIvory II (or was, when I got mine,
a year ago). You may want to budget for more memory (in case the
default is now 16MB), and possibly also a Symbolics keyboard & mouse.

-- 
Raymond Wiker                        Mail:  ·············@fast.no
Senior Software Engineer             Web:   http://www.fast.no/
Fast Search & Transfer ASA           Phone: +47 23 01 11 60
P.O. Box 1677 Vika                   Fax:   +47 35 54 87 99
NO-0120 Oslo, NORWAY                 Mob:   +47 48 01 11 60

Try FAST Search: http://alltheweb.com/
From: Julian St.
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <5rofkoq0ya.fsf@blitz.comp.com>
Brian P Templeton <···@tunes.org> writes:


[...]

> You can get a LispM for $600 from Symbolics, IIRC.

[...]

Is there a free emulator around just to get the look&feel of a lisp
machine?

Regards,
Julian Stecklina
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215999167870810@naggum.net>
* Bruce Hoult
| Every time I or Andreas or someone else is interested in learning about
| and comparing the way CL does something with the way that other
| langauges do similar things, you for some reason I don't fathom
| immediately think that they want to *change* CL.

  NO, you imbecile.  It is that you want to make people feel their teeth
  with their tongue.  Normal people walk through their entire life not
  feeling their teeth with their tongue.  But, if something goes wrong,
  they keep feeling them all the time, and then they pay someone to fix it.
  What you are doing is to tell people that their teeth are wrong, when in
  fact they are not.  You run around like a headless chicken in this
  community and tell people that should feel their teeth because they have
  flaws that only you were smart enough to notice.  And so many people feel
  their teeth with their tongues, and make funny faces.  Then they have to
  explain to others why they are feeling their teeth with their tongue, and
  so lots of people get insecure about their teeth who were perfectly happy
  with them up until then.  This would raise "awareness" of something that
  really needs to be the subject of no awareness whatsoever, because it
  uses resources and concentration that should have had productive use.

  This would actually be a great thing to do for a _really_ devious dentist.

  But then you are so incredibly, insufferably annoying to tell people that
  "no, no, no, I do not want you to _change_ your teeth, there is nothing
  to fix, really, but just keep feeling your teeth, because I think it is
  so amusing to watch all you people make funny faces".   Then you do not
  grasp the first thing about people's reaction to your idiotic behavior.

| Astounded.

  Really?  Your ability to reason about what you do seems thinner than the
  homeopathic soup made by boiling the shadow of a pigeon starved to death.

  Dylan freaks seem so obsessed with their language they would kill their
  own mothers just so they could use the skin to make a drum to beat their
  own praises.

  That _widely_ used language seems utterly unspoilt by failure, and if its
  proponents should occasionally have stumbled across the truth, they have
  hastily picked themselves up and hurried on as if nothing had happened.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Xah Lee
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <B82BA9B9.4DAE%xah@best.com>
> From: Erik Naggum <····@naggum.net>
> Organization: Naggum Software, Oslo, Norway
> Newsgroups: comp.lang.lisp
> Date: Thu, 29 Nov 2001 05:06:10 GMT
> Subject: Re: On nil qua false [was: Re: On conditionals]
> 
> * Bruce Hoult
> | Every time I or Andreas or someone else is interested in learning about
> | and comparing the way CL does something with the way that other
> | langauges do similar things, you for some reason I don't fathom
> | immediately think that they want to *change* CL.
> 
> NO, you imbecile.  It is that you want to make people feel their teeth
> with their tongue.  Normal people walk through their entire life not
> feeling their teeth with their tongue.  But, if something goes wrong,
> they keep feeling them all the time, and then they pay someone to fix it.
> What you are doing is to tell people that their teeth are wrong, when in
> fact they are not.  You run around like a headless chicken in this
> community and tell people that should feel their teeth because they have
> flaws that only you were smart enough to notice.  And so many people feel
> their teeth with their tongues, and make funny faces.  Then they have to
> explain to others why they are feeling their teeth with their tongue, and
> so lots of people get insecure about their teeth who were perfectly happy
> with them up until then.  This would raise "awareness" of something that
> really needs to be the subject of no awareness whatsoever, because it
> uses resources and concentration that should have had productive use.


That's very funny and apropos. Superbly done. It had me laughing.

--

Dear Dylan lovers, i'd suggest you guys leave Common Lispers alone. It's an
old language obsesses by old people who will be dead anytime soon. In
Chinese there's a saying "The new waves pushes the old waves in Yangtze
River". It means that younger generation takes over old generation with
respect to progress. This is nature's way as a dictatorship and mass
murderer. Old people are preordained to die. They hold power, but not for
long. They guide and inspire the younger generation then they drop dead.
Unpleasant thought, to be sure, but divine order.

In computer languages, there's Common Lisp, then there's Scheme and Dylan
and Haskell et al. Sure, lisp evolves and hangs on. Let's hope it live long
and prosper. Still, there are hungry generations awaiting its death, so that
more resources are available for the young.

I advise you younger generation to leave the lispers alone. Don't bother
study lisp, but instead master your Dylan or Haskell or Mathematica. Write
an application or two. If you have extra time, master one or two
mathematics. A theory of graphs, a course of symbolic logic, an
understanding of an algebra, a look at denotational semantics for examples.
If you must get into science history, then nose about history of
mathematics. There you'll learn how humanity's most significant intellectual
ideas evolve. This will give you far more insights to computer language
linguistics than the petty history of lisp. To appreciate math history, you
do need proportional understanding of mathematics. (you pretty much need to
be familiar with subject X to appreciate the history of X.) If you have no
hankering for math history, then you might venture into the history of
humanity. There you will learn how trivial are the debates of Common Lisp vs
Scheme vs Dylan, or C vs C++ vs Java that you see daily in newsgroups and
websites by living zombies who oftentimes never thought of the context of
their discussion, nor what they are talking about. If you dig deep, you'll
see how insignificant are even sciences. (what good is knowledge of sciences
when your wife is fucked by hypocrites and your daughters made into feminism
asses and your sons political asses and your parents drugged by religion and
your siblings blind firebrands and your government and community chaotic and
helpless?) How it will benefit you by learning the history of humanity is
really dependant on each person. You will at the very least not sounding
like a moron among elites. With luck, i wish you young to become the next
great philosophers and social leaders, if not the best scientists.

Knowledge and Love; Goody and goody.

 Xah
 ···@xahlee.org
 http://xahlee.org/PageTwo_dir/more.html
From: Christian Lynbech
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <ofy9kog05x.fsf@chl.ted.dk.eu.ericsson.se>
>>>>> "Xah" == Xah Lee <···@best.com> writes:

Xah> Dear Dylan lovers, i'd suggest you guys leave Common Lispers
Xah> alone. It's an old language obsesses by old people who will be
Xah> dead anytime soon.

This is not to question your definition of "old people" (I am younger
than lisp) but I for one does not hope to be dead anytime soon.

                                 ---

It was the dawn before the night of the full moon. The wise one rose
slowly from the high seat at the fire and gazed in the direction of
the rising sun.

Slowly he spoke: "Common Lisp and its descendants shall be dancing on
the graves of the mortal ones."

                                 ---

------------------------+-----------------------------------------------------
Christian Lynbech       | Ericsson Telebit, Skanderborgvej 232, DK-8260 Viby J
Phone: +45 8938 5244    | email: ·················@ted.ericsson.dk
Fax:   +45 8938 5101    | web:   www.ericsson.com
------------------------+-----------------------------------------------------
Hit the philistines three times over the head with the Elisp reference manual.
                                        - ·······@hal.com (Michael A. Petonic)
From: Alain Picard
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <86u1veudrm.fsf@gondolin.local.net>
Erik Naggum <····@naggum.net> writes:

> 
>   NO, you imbecile.  It is that you want to make people feel their teeth
>   with their tongue.  [SNIP!]

Is it just me, or was that the most _HILARIOUS_ thing _EVER_ posted
to this newsgroup?  I'm verging on tears...   Hee heee,   oof.

Well, they say laughter is good for your health.  Thanks, Erik!


p.s. of course, now I'm gonna "feel" my teeth all evening... but it
     was worth it.  :-)

-- 
It would be difficult to construe        Larry Wall, in  article
this as a feature.			 <·····················@netlabs.com>
From: Lars Lundback
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3c0610cd.24454986@vulkan.euv-frankfurt-o.de>
On 29 Nov 2001 20:28:45 +1100, Alain Picard <·······@optushome.com.au>
wrote:

>Erik Naggum <····@naggum.net> writes:
>
>> 
>>   NO, you imbecile.  It is that you want to make people feel their teeth
>>   with their tongue.  [SNIP!]
>
>Is it just me, or was that the most _HILARIOUS_ thing _EVER_ posted
>to this newsgroup?  I'm verging on tears...   Hee heee,   oof.
>
>Well, they say laughter is good for your health.  Thanks, Erik!
>

Not only you, I too stand up. Pure sarcasm is the best blade.
Applaudes and cheers. 

Lars
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87vgfs983p.fsf@teonanacatl.andreas.org>
Erik Naggum <····@naggum.net> writes:

>   NO, you imbecile.  It is that you want to make people feel their teeth
>   with their tongue.  Normal people walk through their entire life not
>   feeling their teeth with their tongue.  But, if something goes wrong,
>   they keep feeling them all the time, and then they pay someone to fix it.
>   What you are doing is to tell people that their teeth are wrong, when in
>   fact they are not.  You run around like a headless chicken in this

No, what we're doing is trying to compare what other people are
feeling to what we feel, to figure out whether *our* teeth need to be
fixed, for sticking one's tongue in somebody elses mouth over USENET
is a little difficult.

>   with them up until then.  This would raise "awareness" of something that
>   really needs to be the subject of no awareness whatsoever, because it
>   uses resources and concentration that should have had productive use.

It seems the finer points of the discussion are lost on you.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfw3d20nt3y.fsf@shell01.TheWorld.com>
·········@gmx.net (Julian St.) writes:

> Brian P Templeton <···@tunes.org> writes:
> 
> 
> [...]
> 
> > You can get a LispM for $600 from Symbolics, IIRC.
> 
> [...]
> 
> Is there a free emulator around just to get the look&feel of a lisp
> machine?

The original Symbolics is out of business but another has taken its place
and is just barely eeking by.  It SELLS the emulator.  Please do not 
begrudge them that limited income stream.
From: israel r t
Subject: Symbolics current status ( emulator etc )
Date: 
Message-ID: <acdf2usjkajp6eqn7dpjgrmpilq7t6kkbu@4ax.com>
On Mon, 24 Dec 2001 22:36:17 GMT, Kent M Pitman <······@world.std.com>
wrote:

>The original Symbolics is out of business but another has taken its place
>and is just barely eeking by.  It SELLS the emulator.  Please do not 
>begrudge them that limited income stream.

from http://stony-brook.scrc.symbolics.com/www/index.html

" One of the old Symbolics' last products was a port of this
environment to the Compaq/DEC Alpha workstation, called "Open Genera
1.0".

Open Genera 2.0 is available from Symbolics Technology, Inc. It
includes software formerly sold as separate products (Statice, Joshua,
Concordia, Fortran, C, Pascal) and runs under Compaq/Digital Tru64
Unix on Compaq/DEC Alpha workstations. "

Kalman Reti is the bloke to contact at either ····@symbolics.com or at
····@ai.mit.edu
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcvbsgnnl9s.fsf@conquest.OCF.Berkeley.EDU>
Kent M Pitman <······@world.std.com> writes:

> ·········@gmx.net (Julian St.) writes:
> 
> > Brian P Templeton <···@tunes.org> writes:
> > 
> > 
> > [...]
> > 
> > > You can get a LispM for $600 from Symbolics, IIRC.
> > 
> > [...]
> > 
> > Is there a free emulator around just to get the look&feel of a lisp
> > machine?
> 
> The original Symbolics is out of business but another has taken its place
> and is just barely eeking by.  It SELLS the emulator.  Please do not 
> begrudge them that limited income stream.

I doubt it's a grudge, but more of a wish.  It's reasonable for a
tiny, barely surviving company to not give away free or cheap demos,
but $600 is a lot to drop for something you've heard highly
reccomended, but have no experience with yourself.

One thing you *can* fault Symbolics for is that crappy, useless web
site.  Unless you already know the answer, it doesn't provide any
information.  A simple summary of their products would probably answer
that question for most people, as opposed to leaving them confused and
wondering.

Once again, no MacIvory for chiristmas (nuts) :-)

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3C29049A.BC364613@nyc.rr.com>
"Thomas F. Burdick" wrote:
> 
> One thing you *can* fault Symbolics for is that crappy, useless web
> site.  

Amen, I went over there half inclined to plop for one but damned if I
could figure out what I was looking at it.

So what do they have? LispM on a board? I have a couple of Macs
gathering dust, is macIvory a good way to go? I'll try again on Google,
but clues are welcome.

Also, what is supposed to be so great about the LispM? Performance?
Development tools?

thx,

kenny
clinisys
From: Paolo Amoroso
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <+KkpPN0ZpPTq16e35F2bfXGDUdRI@4ax.com>
On Tue, 25 Dec 2001 22:54:55 GMT, Kenny Tilton <·······@nyc.rr.com> wrote:

> "Thomas F. Burdick" wrote:
> > 
> > One thing you *can* fault Symbolics for is that crappy, useless web
> > site.  
> 
> Amen, I went over there half inclined to plop for one but damned if I
> could figure out what I was looking at it.

You may try this site:

  A few things I know about LISP Machines
  http://fare.tunes.org/LispM.html


Paolo
-- 
EncyCMUCLopedia * Extensive collection of CMU Common Lisp documentation
http://web.mclink.it/amoroso/ency/README
[http://cvs2.cons.org:8000/cmucl/doc/EncyCMUCLopedia/]
From: Brian P Templeton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87666kkrht.fsf@tunes.org>
Kenny Tilton <·······@nyc.rr.com> writes:

> "Thomas F. Burdick" wrote:
>> 
>> One thing you *can* fault Symbolics for is that crappy, useless web
>> site.  
> 
> Amen, I went over there half inclined to plop for one but damned if I
> could figure out what I was looking at it.
> 
> So what do they have? LispM on a board? I have a couple of Macs
> gathering dust, is macIvory a good way to go? I'll try again on Google,
> but clues are welcome.
> 
I'm planning to get a Symbolics 3600 LispM. They're $600 US; as Tril
<····@tunes.org> put it, ``cheaper per pound than a good hamburger''.
I don't know how much MacIvory costs. As Paolo mentioned, Far�'s WWW
page about LispMs is an excellent source of information.

> Also, what is supposed to be so great about the LispM? Performance?
> Development tools?
> 
The performance is not too good compared to newer machines. However,
many Lisp programmers who are familiar with them think that they are,
overall, the best available system, despite the mediocre performance.
(However, the emulator for Alpha machines and possibly MacIvory
probably have much better performance.)

> thx,
> 
> kenny
> clinisys

hth,
-- 
BPT <···@tunes.org>	    		/"\ ASCII Ribbon Campaign
backronym for Linux:			\ / No HTML or RTF in mail
	Linux Is Not Unix			 X  No MS-Word in mail
Meme plague ;)   --------->		/ \ Respect Open Standards
From: Barry Margolin
Subject: Value of Open Genera (was Re: On nil qua false [was: Re: On conditionals])
Date: 
Message-ID: <IamW7.5$Mv6.27834@burlma1-snr2>
In article <···············@conquest.OCF.Berkeley.EDU>,
Thomas F. Burdick <···@conquest.OCF.Berkeley.EDU> wrote:
>I doubt it's a grudge, but more of a wish.  It's reasonable for a
>tiny, barely surviving company to not give away free or cheap demos,
>but $600 is a lot to drop for something you've heard highly
>reccomended, but have no experience with yourself.

You get an awful lot of stuff for that $600.  You start with an operating
system far better than just about anything else available (it blows Windows
and Unix out of the water -- MacOS is the only popular OS that even
approaches it in elegance).  You get compilers for 4 programming languages
(Lisp, C, Pascal, Fortran).  You get an Object-Oriented Database System
(Statice) and an AI subtrate (Joshua).  And you get a hypertext
documentation system that predated the WWW by 5 years.

All for twice the price of Microsoft Word.

-- 
Barry Margolin, ······@genuity.net
Genuity, Woburn, MA
*** DON'T SEND TECHNICAL QUESTIONS DIRECTLY TO ME, post them to newsgroups.
Please DON'T copy followups to me -- I'll assume it wasn't posted to the group.
From: Jochen Schmidt
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <9u0n7n$pds$2@rznews2.rrze.uni-erlangen.de>
  # Kenny Tilton <·······@nyc.rr.com> wrote to Bruce Hoult:
  | One of the things I sense about Lisp is that it has developed for a very
  | long time under the hands of folks who are insanely obsessed with doing
  | the Right Thing, and I think a large part of the determination of what
  | is the Right Thing comes from What Would A Reasonable Person Expect. And

# Andreas Bogk answered to Kenny Tilton:
| I hoped that it would be like this.
| 
| But I'm seeing a lot of "Common Lisp does it that way and you need to
| swallow it", and a lot of people who seem to have forgotten that
| Common Lisp is man-made (and even designed by a committee and full of
| bad compromises and legacy crap).

No you don't have to swallow it. You can decide to use CL or not but 
bitching around on things that _you_ as a non-CL user don't like is not 
particularily fair.

The points critizized here in this thread (nil/false/'()...) seem to be no
"bug" or "design-error" to the _users_ of the language but instead of that 
- a _feature_ . It is simply not enough to conclude that it is a 
design-error in Common Lisp if it could be counted as a design-error in a 
completely other language (like Dylan - if you count that as lisp or not).

Do you think it is a good idea for a basketball player to go to a football 
club and criticizing them for using the feet to hit the ball because this 
is a particular bad idea in contrast to the higher agility they would have 
using their hands?

Another claim you mindlessly reuse here as a fact is that nonsense that a 
language designed by a commitee is bad from it's beginnings. Compromises do 
not _need_ to be bad - sometimes a compromise is (seen at a whole) _much_ 
better than any of the possible extremes. The good thing of design by a 
(good) commitee (like in any good democraty) is that it is seldom that 
_critical_ flaws end up in the result.

# Andreas Bogk continues to answer to Kenny Tilton:
| We folks from the Dylan community see ourselves as part of the Lisp
| community.  That's not only because most of the Dylan designers were
| also involved in the Common Lisp standardization process, but also
| because the heritage shows in a lot of places, ranging from the object
| system (modelled after CLOS), the optimzation theory (type
| annotations), first class functions, to the UI framework (CLIM
| vs. DUIM), the general compiler theory etc.  We're interested in an
| honest discussion on what the Right Thing is (and yes, Dylan has it's
| shortcomings too).

I personally see it as a bad point that Dylan omitted s-expressions since 
they are an important part of the "magic" behind lisp. But I don't think 
that Dylan is broken because of this fact - it simply changed it's audience 
to people that do not see or do not want the benefits of s-expression 
notation. The bad thing is that some Dylan users tend to claim to new users 
interested in lisp that Dylan is unconditionally better for them because it 
does not have "this many ugly parens". This claims imply that it is a 
bug to have s-expressions and even worse - it omits that it is maybe a 
_loss_ for Dylan not having them!!!

The bad thing when discussing about "The Right Thing" is that it simply 
does not exist out of context. A particular language, a community and even 
an implementation all define contexts that have to be taken into account 
when searching for "the Right Thing". Even if the context is well defined 
it happens from time to time that "the Right Thing" is ambiguous.

I'm too very interested in discussing language issues - but I think it is 
not a _honest_ discussion if on participant claims that the others are 
wrong because _oneself_ did it the other way! 

Ask yourself what the real reasons are behind that particular wish of 
discussion - is it _really_ for finding the "Right Thing"? (which would 
imply to be _open_ for solutions that are different to your own!) Or is it 
maybe more like pushing of the own way to others?
Is this _really_ about investigating if CL is good or what could be done 
better in Dylan? To me it looks more like marketing and advertising Dylan 
here in c.l.l - and not like "honest discussion".

ciao,
Jochen

--
http://www.dataheaven.de
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87adx7gbcf.fsf@teonanacatl.andreas.org>
Jochen Schmidt <···@dataheaven.de> writes:

> No you don't have to swallow it. You can decide to use CL or not but 
> bitching around on things that _you_ as a non-CL user don't like is not 
> particularily fair.

Just that I am a non-CL user (yet, I wish I would get clg working...),
doesn't mean I cannot imagine what it would be like to work with a
Lisp where nil equals '().  Especially since I have enjoyed working
with languages that differentiate, and appreciate the coherency
resulting from following stricter design criteria.

> The points critizized here in this thread (nil/false/'()...) seem to be no
> "bug" or "design-error" to the _users_ of the language but instead of that 
> - a _feature_ . It is simply not enough to conclude that it is a 
> design-error in Common Lisp if it could be counted as a design-error in a 
> completely other language (like Dylan - if you count that as lisp or not).

As a feature, it feels like a convenience hack so you can write 
(if foo) instead of (unless (empty? foo)).

That's not much of a gain, given that you have just violated the
design rule of having a way to differentiate between a valid and an
invalid result.  So you're having a potential pitfall here that you
need to be aware of when writing code.  This might feel natural after
having developed awareness for the phenomenon and trained avoiding it.
Still, it adds to the learning curve for newcomers, and potentially
uses up cycles in your brain that you could use to solve the actual
problem instead.

> Do you think it is a good idea for a basketball player to go to a football 
> club and criticizing them for using the feet to hit the ball because this 
> is a particular bad idea in contrast to the higher agility they would have 
> using their hands?

No. The rules are fixed and simple. I could see different basketball
teams having an argument about a basketball rule, however.  I could
also see an argument about training methods for underlying basic
primitives of movements and physical abilities.

> Another claim you mindlessly reuse here as a fact is that nonsense that a 
> language designed by a commitee is bad from it's beginnings. Compromises do 
> not _need_ to be bad - sometimes a compromise is (seen at a whole) _much_ 
> better than any of the possible extremes. The good thing of design by a 
> (good) commitee (like in any good democraty) is that it is seldom that 
> _critical_ flaws end up in the result.

As with laws, it's hard to see afterwards what the compromises
involved were.  Judging from what I've read in several documents about
the history of Lisp, CL was a rather hairy compromise.

Of course, not all committee results are bad.  I just sometimes have
that imagination of a painting designed by a committee of Rembrandt,
Van Gogh and Dali.

> I personally see it as a bad point that Dylan omitted s-expressions since 
> they are an important part of the "magic" behind lisp. But I don't think 

How would you feel about reviving the prefix Dylan syntax?

> that Dylan is broken because of this fact - it simply changed it's audience 
> to people that do not see or do not want the benefits of s-expression 
> notation. The bad thing is that some Dylan users tend to claim to new users 

One of the things on my list is finding out whether this benefit is
really there or if it could be achieved by other means.

> interested in lisp that Dylan is unconditionally better for them because it 
> does not have "this many ugly parens". This claims imply that it is a 
> bug to have s-expressions and even worse - it omits that it is maybe a 
> _loss_ for Dylan not having them!!!

That's just to lure in the newbies, in whose eyes this *is* a bug.  In
my view, it's a minor inconvenience that I don't actually mind
anymore, and probably just a cultural thing.  For me, the Dylan syntax
is better readable, because it provides more context to my eye.  I can
spot assignments in infix Dylan immediately, whereas it takes me
several seconds to locate an assignment in prefix code.  Same goes for
grokking arithmetic expressions and array access.

The s-expression argument comes up quite often.  Why not, as an
experiment, start telling the newbies that, even though you think
s-expressions are superior, they can try Dylan to learn the basic
concepts, and then come back later to learn about advanced concepts.

> The bad thing when discussing about "The Right Thing" is that it simply 
> does not exist out of context. A particular language, a community and even 
> an implementation all define contexts that have to be taken into account 
> when searching for "the Right Thing". Even if the context is well defined 
> it happens from time to time that "the Right Thing" is ambiguous.

Discussing the Right Thing naturally boils down to discussing the
context, and that's productive.

> I'm too very interested in discussing language issues - but I think it is 
> not a _honest_ discussion if on participant claims that the others are 
> wrong because _oneself_ did it the other way! 

I promise not to do that.  But I might claim that someone is wrong if
he presents an argument that contradicts a common context we've
established before.  If in his model there is no contradiction, he
must be using different axioms than me, and isolating these
differences can be a rewarding insight to both participants of the
discussion.  That would perfectly refute my claim of wrongness.

> Ask yourself what the real reasons are behind that particular wish of 
> discussion - is it _really_ for finding the "Right Thing"? (which would 
> imply to be _open_ for solutions that are different to your own!) Or is it 
> maybe more like pushing of the own way to others?

It's Yin and Yang.  I can only establish facts about how important an
argument is to someone by trying to push them.  It is polite to keep
that push as small as possible, and a strong reaction to a small push
indicates a big force not originating from me.  I am fully aware that
this might push me around too, and I don't insist on not moving.  I
just believe that we all might end up in a constellation much more
beneficial for all.

> Is this _really_ about investigating if CL is good or what could be done 
> better in Dylan? To me it looks more like marketing and advertising Dylan 
> here in c.l.l - and not like "honest discussion".

If you consider it advertising when I'm saying that Dylan was a good
idea, then yes, I am advertising.  But it's honest, since that's my
opinion that I can back with arguments, and I can be convinced
otherwise with better arguments.

I do not mean to flame, troll, or insult people.  I'm coming here with
an open mind, and a story to tell.  I hope I'm finding people here of
likewise ilk.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Bradford W. Miller
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <B8296E2A.11AC%Bradford.W.Miller@motorola.com>
For a summary of the NIL/False dichotomy (and why to overload them) see

"A Short Ballad Dedicated to the Growth of Programs" by Ashwin Ram

http://www.lisp.org/humor/large-programs.html

Best,
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87r8qjeowq.fsf@teonanacatl.andreas.org>
"Bradford W. Miller" <·················@motorola.com> writes:

> "A Short Ballad Dedicated to the Growth of Programs" by Ashwin Ram
> http://www.lisp.org/humor/large-programs.html

Nice read.  For comparison, here's the idiom the author seeked in
Dylan:

element(a-list, key, default: #f)

which even works regardless of the type of the collection like lists,
hashtables and vectors, and which allows for an alternative default
value in case #f is a legal element of a-list.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Marco Antoniotti
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <y6citbvq6ps.fsf@octagon.mrl.nyu.edu>
Andreas Bogk <·······@andreas.org> writes:

> "Bradford W. Miller" <·················@motorola.com> writes:
> 
> > "A Short Ballad Dedicated to the Growth of Programs" by Ashwin Ram
> > http://www.lisp.org/humor/large-programs.html
> 
> Nice read.  For comparison, here's the idiom the author seeked in
> Dylan:
> 
> element(a-list, key, default: #f)
> 
> which even works regardless of the type of the collection like lists,
> hashtables and vectors, and which allows for an alternative default
> value in case #f is a legal element of a-list.

This argument can be turned on its head.  As an example, the *ML* crowd
(Haskell included), would argue that either you'd have to program a
special failure value into the alist data type, or that an exception
should be raised if no value were to be found.

ASSOC, FIND and friends are annoying, as (agreeing with Paul Graham)
it is somewhat annoying to have separate abstractions for table
lookups.

This is somewhat strange and an oversight in view of the fact that
GETHASH does the right thing.  It accepts a default and returns two
values.

Cheers

-- 
Marco Antoniotti ========================================================
NYU Courant Bioinformatics Group        tel. +1 - 212 - 998 3488
719 Broadway 12th Floor                 fax  +1 - 212 - 995 4122
New York, NY 10003, USA                 http://bioinformatics.cat.nyu.edu
                    "Hello New York! We'll do what we can!"
                           Bill Murray in `Ghostbusters'.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-D5891D.13081628112001@news.paradise.net.nz>
In article <·······························@motorola.com>, "Bradford W. 
Miller" <·················@motorola.com> wrote:

> For a summary of the NIL/False dichotomy (and why to overload them) see
> 
> "A Short Ballad Dedicated to the Growth of Programs" by Ashwin Ram
> 
> http://www.lisp.org/humor/large-programs.html

        (cdr (assq key a-list))

vs

        (let ((val (assq key a-list)))
           (cond ((not (null? val)) (cdr val))
                 (else nil)))


What would be wrong with:

        (element a-list key :default nil)

??

-- Bruce
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3C0430A9.5DEB48B8@nyc.rr.com>
Bruce Hoult wrote:
> 
> In article <·······························@motorola.com>, "Bradford W.
> Miller" <·················@motorola.com> wrote:
> 
> > For a summary of the NIL/False dichotomy (and why to overload them) see
> >
> > "A Short Ballad Dedicated to the Growth of Programs" by Ashwin Ram
> >
> > http://www.lisp.org/humor/large-programs.html

Ah, that's the piece I was thinking of quite a few dead horses back.
Priceless.

> 
>         (cdr (assq key a-list))
> 
> vs
> 
>         (let ((val (assq key a-list)))
>            (cond ((not (null? val)) (cdr val))
>                  (else nil)))
> 
> What would be wrong with:
> 
>         (element a-list key :default nil)

I do not know either language and take your word for it that your
offering is the same as the lisp version, but I think that misses the
point of the spoof, viz, what happens /in general/ when NIL and false
are different. ie, CMIIW one cannot always avoid horrors such as:

    (not (null? <x>)) 

and:

    (else nil)

..with some language feature such as (element...).


kenny
clinisys
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87elmjel17.fsf@teonanacatl.andreas.org>
Kenny Tilton <·······@nyc.rr.com> writes:

> are different. ie, CMIIW one cannot always avoid horrors such as:
> 
>     (not (null? <x>)) 
> 
> and:
> 
>     (else nil)

A idiom one commonly sees in a number of Lisps is

  (and x (some-operation-that-fails-on-false x))

which would read

  x & x.some-operation-that-fails-on-false

in infix Dylan.  If the compiler[0] knows that the type of x is
false-or(<x>), it can even prove that x will never be false for
some-operation, and optimize away type checks, function dispatch and
the like.

Note that if the result of some-operation is <y>, the type of the
complete expression above would be false-or(<y>).

Andreas

[0] A smart enough compiler. Functional Developer is, Gwydion Dylan
    isn't.

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-DE86EC.16224128112001@news.paradise.net.nz>
In article <··············@teonanacatl.andreas.org>, Andreas Bogk 
<·······@andreas.org> wrote:

>   x & x.some-operation-that-fails-on-false
> 
> in infix Dylan.  If the compiler[0] knows that the type of x is
> false-or(<x>), it can even prove that x will never be false for
> some-operation, and optimize away type checks, function dispatch and
> the like.

Gwydion handles this just fine if x is a simple binding.  What it 
doesn't do (and bug reports have been submitted about) is optimize:

   foo(x) & foo(x).some-operation-that-fails-on-false

or (equivilently)

   x.foo & x.foo.some-operation-that-fails-on-false


Of course in general you can't optimize this because foo() might have 
side effects, but in the special case of foo() being a 
compiler-generated slot getter (which is what the bug reports were 
about) the compiler can safely assume that there are no side effects and 
CSE it.  Gwydion doesn't (yet) do this.

At one time I thought that it was correct to not CSE slot access because 
the value of the slot could be changed by another thread (which can't 
happen with a local binding), but then some of the folks who originally 
designed Dylan said that there was no intention to enforce thread-safety 
at that granularity.

-- Bruce
From: Lieven Marchand
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <m31yijoqzg.fsf@localhost.localdomain>
Andreas Bogk <·······@andreas.org> writes:

> Of course, not all committee results are bad.  I just sometimes have
> that imagination of a painting designed by a committee of Rembrandt,
> Van Gogh and Dali.

In more artisanal times, like Rubens and probably Rembrandt still, a
painting was a committee work, where the master did the composition,
the foreground and other import stuff and one of his students might
fill in a tree or clouds in the background.

-- 
Lieven Marchand <···@wyrd.be>
She says, "Honey, you're a Bastard of great proportion."
He says, "Darling, I plead guilty to that sin."
Cowboy Junkies -- A few simple words
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87vgfubpc8.fsf@teonanacatl.andreas.org>
Lieven Marchand <···@wyrd.be> writes:

> In more artisanal times, like Rubens and probably Rembrandt still, a
> painting was a committee work, where the master did the composition,
> the foreground and other import stuff and one of his students might
> fill in a tree or clouds in the background.

Committees work different.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215996601432739@naggum.net>
* Andreas Bogk
| Committees work different.

  I think you meant to say that you know for certain that all committees
  are _exactly_ alike, because you have been to at least one meeting of at
  least one committee.  You should make clear to those of us who have been
  members of many committees and have not seen this incredibly simple truth
  or indeed discovered your Grand Unifying Theory of Committees, that we
  are mistaken and have been deluded.  There is actually only one committee
  in the whole world, and it is run by telepathic extraterrestial aliens
  who want to remove individual freedom, and they were also behind the 9/11
  attack and now George W. Bush is turning the U.S.A. into a dictatorship
  where Chinese legal practices against "national security" is becoming
  increasingly popular with that Ashcroft figure.  The Committee was also
  behind the Common Lisp standard.  Dylan somehow escaped the death grip of
  The Committee and is the last bastion of individual freedom on earth, our
  last hope against alien take-over.  Therefore, the only remaining hope
  for mankind is that Dylan take over the world.

  "Committees work different."  Really.  Dude, are you fucking _nuts_?

  Dylan, being a rebellious child of Lisp, is attacking the parens.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87lmgp9q59.fsf@teonanacatl.andreas.org>
Erik Naggum <····@naggum.net> writes:

>   "Committees work different."  Really.  Dude, are you fucking _nuts_?

You're still as offensive as before...

>   Dylan, being a rebellious child of Lisp, is attacking the parens.

... but funnier.

I guess I delay killfiling you for a few more days.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215919589232206@naggum.net>
* Andreas Bogk <·······@andreas.org>
| Just that I am a non-CL user (yet, I wish I would get clg working...),
| doesn't mean I cannot imagine what it would be like to work with a
| Lisp where nil equals '().

  People who imagine things that are not so, have a very strange tendency
  to believe that other things remain unchanged which would be _very_
  different if their simple "change" were indeed made.  It takes a very,
  very smart person to lie consistently about something for a long time
  without being exposed, because all things interconnect and two things
  that would normally exclude eachother seem to be true at the same time.
  The unusual ability of liars to explain apparent contradictions is one of
  the things that give them away.  The knowledge of the world possessed by
  honest people is limited in strange and unpredictable ways, and sooner or
  later, you run into something they cannot explain, but this is _normal_.
  A person who has constructed a make-believe world has had to make up so
  much that the boundaries of their knowledge tend to be more predictable
  and they exceed other people in their detailed knowledge of their world,
  because of their fear that the unexplainable will give them away.  Even
  knowing this, it is extremely hard to lie convincingly -- those who are
  best at it write long novels, which differ from other elaborate lies in
  that they do not even _intend_ to be true.

  In other words, I strongly doubt that you can.

| As a feature, it feels like a convenience hack so you can write 
| (if foo) instead of (unless (empty? foo)).

  Is this the extent of your imagination?

| That's not much of a gain, given that you have just violated the design
| rule of having a way to differentiate between a valid and an invalid
| result.

  Where the hell did this rule come from?  I thought you had rejected laws
  that were immoral or meaningless because your upbrining in dictatorships.
  What makes you even _believe_ that you can dictate such rules and _not_
  have people object to the nonsense?

| Still, it adds to the learning curve for newcomers, and potentially uses
| up cycles in your brain that you could use to solve the actual problem
| instead.

  As a matter of fact, (when foo ...) has a _much_ lower cognitive load
  than (unless (empty? foo) ...).  If you at _least_ had rewritten it as
  (when (pair? foo) ...), you might have a fighting chance, but the two are
  not quite similar -- foo could be a non-list, in which case empty? might
  provide the wrong answer.  An empty string or vector or hashtable or
  package or whatever is true in Common Lisp, but empty? should be true of
  all of these.  You would in fact have to be

(unless (or (not (list? foo)) (not (pair? foo))) ...)

  to be an accurate "translation", or you could of course write

(unless (not (eql foo <false>)) ...)

  which just proves that (when foo ...) is the _correct_ choice!

| As with laws, it's hard to see afterwards what the compromises involved
| were.  Judging from what I've read in several documents about the history
| of Lisp, CL was a rather hairy compromise.

  That _should_ tell you something about people, _not_ about languages.

| I just sometimes have that imagination of a painting designed by a
| committee of Rembrandt, Van Gogh and Dali.

  When I see people denounce the work of several people who work together,
  I see a person who thinks _much_ too highly of his own abilities.  Out of
  all the millions, if not billions, of painters in the history of the
  world, the handful of geniuses who _did_ paint better than a committee
  would have done actually prove that committees do a better job than the
  (- total-world-population number-of-geniuses) people would.  However, if
  you think of _yourself_ as the Rembrandt of programming language design,
  this may be hard to understand.  However, since irrationally exaggerated
  egos tend to cause few problems until they are challenged (at which point
  such people implode and/or become physically violent), staying away from
  people who put a bullet through inflated egos is a good survival tactic,
  as is trying to intimidate anyone who can expose them, and one may in
  fact keep believing that one's ego is the correct size for quite a while.
  E.g., I know a lot of people who are better than me at many of the things
  I want to be good at, but I know far, far more people who only _think_
  they are and who have yet to wake up and smell the coffee and realize
  their "ranking".  These latter people tend to hate me for not allowing
  them to keep thinking they are far better than they are.

| One of the things on my list is finding out whether this benefit is
| really there or if it could be achieved by other means.

  Whether it could or not is irrelevant unless you are designing a new
  language from scratch -- and you do not do that in a newsgroup for an
  established language, at least not under such pretenses as you do.

  The question is whether it should even be attempted.  Smart people can
  figure out better ways to make democracy work, but when people who are
  too smart for their own good get brilliant ideas, they tend to set up
  dictatorships, instead, because the royal mess that is democracy in
  action is actually _much_ worse than _any_ isolated theory could be --
  until implemented.  And that is what makes them _better_, because the
  crucial element of a democracy is that people agree only on what _not_ to
  do, not on what to _do_.  Basically, what they end up doing is a fall-out
  of what they have agreed to _exclude_ from the possibility of being done.
  Given the resources of modern countries, _anything_ could be achieved.
  It is what we give high enough priority that it excludes a lot of stuff
  that actually gets done.  In the budgeting and prioritizing process of
  politics, the actual agreements are over what _not_ to do with all that
  money, what _not_ to bring up again during the budget period.  Budget
  debates are not about the money, but about killing political ideas.

| That's just to lure in the newbies, in whose eyes this *is* a bug.

  So you admit to fraudulent marketing.  Well, good luck with Dylan.

| In my view, it's a minor inconvenience that I don't actually mind
| anymore, and probably just a cultural thing.

  "Just a cultural thing"?  That is precisely what the super-tolerant
  idiots say about the molestation of young females in backward cultures
  that claim it is their "religion" that defends this criminal act against
  at least half of humanity.  Cultures are tremendously important, and some
  of them are just plain _bad_.

  _Culture_ is at the very core of why people choose language communities.

| The s-expression argument comes up quite often.  Why not, as an
| experiment, start telling the newbies that, even though you think
| s-expressions are superior, they can try Dylan to learn the basic
| concepts, and then come back later to learn about advanced concepts.

  Why the hell would Common Lisp users want to do that?  I think you, the
  proposer of this idiotic manipulation attempt, suggest to your Dylan
  users to try out Common Lisp before they tire of Dylan's shortcomings.
  Man, you are so incredibly short-sighted you insult your own intelligence
  with such a stupid, stupid suggestion.  You really _are_ a marketing and
  advertising person, are you not?  Zero technical skills compensated for
  by lots of smooth talking could produce such an incredibly _dumb_ attempt
  to pull the wool over so many people's eyes, but not honesty and smarts.

| Discussing the Right Thing naturally boils down to discussing the
| context, and that's productive.

  That "context" is a large framework of what has been excluded from the
  discussion.  In essence, The Right Thing is whatever is left when you
  have agreed not to pursue a very large number of paths.  It is the same
  way when people say they have chosen their new car through a careful
  process of weighing positive and negative sides, cost and efficiency, and
  can make a perfect explanation for why this car is _the_ best choice.
  What they usually omit from this story is how they "decided" to not even
  consider 99% of the car market before they started weighing anything at
  all and probably were left with a handful of models, if not actual cars,
  based on unexpressed and emotionally determined desiderata, among which
  some _actually_ irrelevant factor was "weighed" and found sufficient.

  To trace the history of how we ended up with our conclusions, ignore all
  the explicit arguments and premises and logic and focus on what went down
  the drain before you even _started_ to think about it.  _That_ is where
  you will find the history.  It is not as accidental as you might think.
  What we do _automatically_ is what defines our sense of culture.  If you
  come from a different culture, you will fail to find the reasons in the
  _explicit_ history of the new culture.  (This is why history is such a
  hard discipline and requires people who are able to put themselves in the
  context of their discoveries.)

  It is fundamentally unproductive to "discuss" the context.  Either you
  grasp it more or less automatically, or you fail to.  If you do not, you
  can find particular reasons why it failed, but if you persist, you will
  only be an outsider looking in at something you do not understand.  If,
  on the other hand, you accept that whatever this new thing is, you should
  let it influence you before you try to influence it, you will slowly grow
  into its frame of mind in ways that are incredibly hard to explain
  because it happens just as implicitly as how two people grow together
  when they live together, how pets and their owners communicate without
  any signs that outsiders can observe, how we attribute this to intuition
  when in fact it is nothing more than the ability to discern signals that
  other people overlook.

  Discussing underlying premises of the tacitly accepted and rejected
  requires specially trained people.  Philosophers and psychologists are
  sometimes able to pick up those underlying premises, but the Heisenberg
  uncertainty principle applies to people, too: just by asking and _making_
  people think about something, you have influenced their thinking and in
  minute ways changed them.  The amount of intellectual attention and
  dedication to detail necessary to prevent errors and both false positives
  and negatives in this process is _frightening_ to the untrained.

  Consequently, I completely fail to see how you can even assume that you
  would be able to conduct and complete this procedure fruitfully without
  massive loss of accuracy even if you did it face to face with people.  In
  fact, I expect that such a procedure would be a total wash on USENET.
  Therefore, discussing the context here _must_ be counter-productive.

| But I might claim that someone is wrong if he presents an argument that
| contradicts a common context we've established before.

  But because you are an outsider by choice, you would not be able to
  determine this.  Someone who decides to learn something fully, has to
  _immerse_ themselves in it before he starts to think too much, or the
  process of immersion and learning and understanding will _fail_.  If you
  start to think too early in the process, you will use your previous
  contexts to validate what you are learning, and that is wrong.  By so
  doing, you will block your ability to validate using a different context,
  unless you are very, very smart and self-aware.  Very few people are.

| If in his model there is no contradiction, he must be using different
| axioms than me, and isolating these differences can be a rewarding
| insight to both participants of the discussion.  That would perfectly
| refute my claim of wrongness.

  Your belief in a logic you have demonstrated a serious lack of ability to
  handle productively is downright charming, but it is so much hard work
  and so painful a process that it must be a matter of _habit_, not a
  matter of studiously conscious procedures done in your sunday clothes
  only when called upon.  If you are sloppy and confused and do not look
  carefully at your observations and conclusions _regularly_, you are not a
  person with whom this process can be expected to produces good results.

  I am looking forward to how well you understand these premises of a
  discussion at the level you seem to seek.  I think it is just as much
  pretense and hogwash as claims to live in a world of "proofs", which is
  also only for show to people who do not think it through.

| It's Yin and Yang.  I can only establish facts about how important an
| argument is to someone by trying to push them.  It is polite to keep
| that push as small as possible, and a strong reaction to a small push
| indicates a big force not originating from me.

  This presupposes that there is a priori and universal agreement on the
  amount of push -- that I cannot think your push was bigger than you think
  it was.  Since this is obviously ridiculous to base an argument on, what
  such a reaction _really_ indicates is most probably that you have failed
  to assess the amount of push you exerted correctly, and particularly so
  because you failed to understand that you relied on an agreement that
  simply _could_ not exist, for your argument to be true.  Such sloppiness
  in thinking that pretends to be logical is actually quite alarming, as it
  indicates that you have never been challenged on its fundementals and
  have been allowed to walk through life thinking much too highly of your
  logical abilities and the guaranteed results of applied logic.  This is
  almost like watching old Star Trek episodes with the ridiculous role of
  Spock, who is "logical" based on a bunch of ludicrous premises.

  The lack of precision and willingness to think through what you are
  saying is downright annoying.  You think too little and talk too much.
  Nice words, looks good to the careless observer, but is just bullshit.
  You simply fail to understand that people do not just disagree on some
  surface issue -- they may disagree all the way down.  Even if you seem to
  agree on _some_ aspects of something, that is absolutely no guarantee
  that this is accidental.  E.g., a realist and an idealist may agree on
  the fruitlessness of homeopathic "medicine" for reasons that look the
  same for a while, but than radically depart on some core principle.
  People can likewise agree on some "Lispness" of their pet languages, but
  strongly disagree that a language that lacks s-expressions in its syntax
  should even pretend to be "a Lisp".

| If you consider it advertising when I'm saying that Dylan was a good
| idea, then yes, I am advertising.  But it's honest, since that's my
| opinion that I can back with arguments, and I can be convinced otherwise
| with better arguments.

  What utter nonsense.  You decided on what made you choose Dylan long
  before you ever heard any "argument" either way.  You will not be swayed
  on any but the most superficial points by arguments.  You will, instead,
  protect yourself from such swaying.  How can I say this so certainly?
  Because you show an amazing lack of insight into how people choose and
  value things.  Of course, now that I have said this, you may think about
  it and you may decide to surprise me.  That would be kind of fun.

| I do not mean to flame, troll, or insult people.  I'm coming here with an
| open mind, and a story to tell.

  You would like to believe so, but it is in fact false.

  If you react _defensively_ to the last line, your mind is _not_ open.

  I think I dislike that trolls that come in nice suits more than the
  stinking homeless bum trolls.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87zo56buo7.fsf@teonanacatl.andreas.org>
Erik Naggum <····@naggum.net> writes:

>   People who imagine things that are not so, have a very strange tendency
>   to believe that other things remain unchanged which would be _very_
>   different if their simple "change" were indeed made.  It takes a very,

Well, that's the reason we're discussing this issue here with people
having the experience, instead of blindly believing our gedanken
experiment.

> | As a feature, it feels like a convenience hack so you can write 
> | (if foo) instead of (unless (empty? foo)).
>   Is this the extent of your imagination?

Well, it extends to a general dislike against any use of inband
signalling in a lot of other contexts.

By the way, the URL of the poem on the topic did a lot more to
enlighten me on the subject: it showed me a typical construct where
nil == '() is useful, and that I need not worry about Dylan doing it
in a way I consider more consistent, because the concerns don't apply.

All I've seen from you, on the other hand, is hundreds of lines of
insult against my person and intelligence, sprinkled with a couple of
interesting, but unrelated insights.

> | That's not much of a gain, given that you have just violated the design
> | rule of having a way to differentiate between a valid and an invalid
> | result.
>   Where the hell did this rule come from?

It's a specialization of the rule of not using inband signalling,
because there might be data that looks like a signal.

>   I thought you had rejected laws
>   that were immoral or meaningless because your upbrining in dictatorships.

I don't consider this rule meaningless.  But not because it is written
down in some text I consider authoritative in what is right or wrong,
but because of a conscious decision that the rule makes sense.

This is based on observation of the problems (especially security
problems) of software that violates these rules.  Prominent examples
are Blueboxing (the ability to make fraudulent calls in C5 PBX systems
by generating tones) and denial of service against modems by sending ICMP
Echo packets with +++ATH0 in them.

I even think there was a security problem in X11 that was based on
sending 2^32-1 bytes of data to the server.  That made some counter
reach -1, which was treated special.  The poor C program promptly
mangled the return pointer on the stack, and an attacker could inject
exploit code.

>   What makes you even _believe_ that you can dictate such rules and _not_
>   have people object to the nonsense?

I do not believe I can dictate such rules.  But I believe this rule is
meaningful, and that a lot of people share it.

So anybody who thinks that CL is better off violating this rule either
doesn't believe in it, or believes that there are more important
rules.  In both cases, I am curious to know why.

>   As a matter of fact, (when foo ...) has a _much_ lower cognitive load
>   than (unless (empty? foo) ...).

Only if you have interned this particular feature so much that you
also see the latter meaning if you see the former in code.

Using the former when meaning the latter fails to communicate the
intent.  

>   If you at _least_ had rewritten it as
>   (when (pair? foo) ...), you might have a fighting chance, but the two are
>   not quite similar -- foo could be a non-list, in which case empty? might
>   provide the wrong answer.  An empty string or vector or hashtable or
>   package or whatever is true in Common Lisp, but empty? should be true of
>   all of these.

The intent when writing such code is indeed testing for an empty
container, so the fact that it works correctly for non-list container
is a good thing.

Too bad this isn't true for the (when foo) case, it only works for
lists.

By the way, please forgive the use of the Dylanesque empty?.  I'm so
used to working in a language where I can express operations on
collections independent of their implementation that I completely
missed the fact that there is no empty? in Common Lisp, and that it
can't be implemented in a way that would have equal performance to
(when foo).

> | I just sometimes have that imagination of a painting designed by a
> | committee of Rembrandt, Van Gogh and Dali.
>   When I see people denounce the work of several people who work together,
>   I see a person who thinks _much_ too highly of his own abilities.  Out of

I've been to some meetings of standardization groups, and have seen
how they work, thank you.  Their compromises are often not mine, and
their documents below the standard of the individual members.

Quite often, what they produce makes the world a better place. Common
Lisp certainly has served it's purpose.  The citation above is just a
nightmare haunting me :)

>   all the millions, if not billions, of painters in the history of the
>   world, the handful of geniuses who _did_ paint better than a committee
>   would have done actually prove that committees do a better job than the
>   (- total-world-population number-of-geniuses) people would.  

Not if it would increase the marketshare of vendor X not to do so.
I'm speaking from experience here (and no, the genius, if he was one,
was not me).

>   However, if you think of _yourself_ as the Rembrandt of
>   programming language design, this may be hard to understand.

I've only been using programming languages for the last 14 years, and
I've only been studying programming language design for the last 5
years, so I'm certainly neither the most experienced language designer
nor the best.

But I think I'm able to judge other people's designs up to a certain
degree.

>   E.g., I know a lot of people who are better than me at many of the things
>   I want to be good at, but I know far, far more people who only _think_
>   they are and who have yet to wake up and smell the coffee and realize
>   their "ranking".

So your participation in this newsgroup has the purpose of
establishing some smartness ranking?

>   These latter people tend to hate me for not allowing
>   them to keep thinking they are far better than they are.

I think most people tend to hate you because of your attitude.  I have
met people smarter *and* more humble than you.

> | One of the things on my list is finding out whether this benefit is
> | really there or if it could be achieved by other means.
>   Whether it could or not is irrelevant unless you are designing a new
>   language from scratch 

It's not irrelevant, it's called "learning".  It might even be of some
use if I ever decide it would be nice to design a new language from
scratch.

But I think slightly improving existing languages is a more realistic
target.

>   until implemented.  And that is what makes them _better_, because the
>   crucial element of a democracy is that people agree only on what _not_ to
>   do, not on what to _do_.  

Do you pay taxes?

> | That's just to lure in the newbies, in whose eyes this *is* a bug.
>   So you admit to fraudulent marketing.  Well, good luck with Dylan.

Imagine a smiley at the end of the line.  A neutral formulation would
be: it reduces the learning curve for newbies that already have used a
language with infix syntax, so we can teach them about more relevant
concepts, like closures, GF dispatch, dynamic types etc.  So the
likelihood is higher that they won't want to go back to languages that
don't offer these features.

> | In my view, it's a minor inconvenience that I don't actually mind
> | anymore, and probably just a cultural thing.
>   "Just a cultural thing"?  That is precisely what the super-tolerant
>   idiots say about the molestation of young females in backward cultures
>   that claim it is their "religion" that defends this criminal act against
>   at least half of humanity.  Cultures are tremendously important, and some
>   of them are just plain _bad_.

Have you just compared infix syntax to child molestation, or is this
just my imagination?

> | The s-expression argument comes up quite often.  Why not, as an
> | experiment, start telling the newbies that, even though you think
> | s-expressions are superior, they can try Dylan to learn the basic
> | concepts, and then come back later to learn about advanced concepts.
>   Why the hell would Common Lisp users want to do that?  I think you, the

Because this was one of the original intents of Dylan, and it works.
Everybody who understands Dylan is a potential user of CL.

>   proposer of this idiotic manipulation attempt, suggest to your Dylan
>   users to try out Common Lisp before they tire of Dylan's shortcomings.

Don't laugh, but I do.

>   Man, you are so incredibly short-sighted you insult your own intelligence
>   with such a stupid, stupid suggestion.  You really _are_ a marketing and
>   advertising person, are you not?  Zero technical skills compensated for
>   by lots of smooth talking could produce such an incredibly _dumb_ attempt
>   to pull the wool over so many people's eyes, but not honesty and smarts.

You're insulting your intelligence with flames and rude behaviour.

I've had several opportunities to demonstrate my technical skills, for
instance leading a development effort for digital TV software with a
team of 40 developers (and my design worked), and recently as a member
of the team winning the second prize at the ICFP2001 contest.

>   To trace the history of how we ended up with our conclusions, ignore all
>   the explicit arguments and premises and logic and focus on what went down
>   the drain before you even _started_ to think about it.  _That_ is where

I think that would be a bad approach.  Logic has it's limits, but it
cannot be plainly rejected as irrelevant.

>   It is fundamentally unproductive to "discuss" the context.  Either you

If you think so, stop discussing with me.  I'm interested, and other
people are too.

>   Discussing underlying premises of the tacitly accepted and rejected
>   requires specially trained people.  Philosophers and psychologists are
>   sometimes able to pick up those underlying premises, but the Heisenberg

That are no skills that can not be learned and made use of in our
field.  Look into any good book on user interface design for examples.
Or look into this newsgroup for that matter: the argument of intent is
of psychological nature, and many of your arguments are philosophical.
Some are rhetorical, for that matter.

>   Consequently, I completely fail to see how you can even assume that you
>   would be able to conduct and complete this procedure fruitfully without
>   massive loss of accuracy even if you did it face to face with people.  In

It's called discussion, and is the prominent purpose of USENET.

>   But because you are an outsider by choice, you would not be able to
>   determine this.  Someone who decides to learn something fully, has to
>   _immerse_ themselves in it before he starts to think too much, or the
>   process of immersion and learning and understanding will _fail_.  If you
>   start to think too early in the process, you will use your previous
>   contexts to validate what you are learning, and that is wrong.  By so
>   doing, you will block your ability to validate using a different context,
>   unless you are very, very smart and self-aware.  Very few people are.

Do you consider yourself to be that smart?  How deeply have you looked
into Dylan, for instance, to be able to say that it doesn't have the
Lisp nature?

>   Your belief in a logic you have demonstrated a serious lack of ability to
>   handle productively is downright charming, but it is so much hard work

You still have to show a serious flaw in my logic.

>   and so painful a process that it must be a matter of _habit_, not a
>   matter of studiously conscious procedures done in your sunday clothes
>   only when called upon.  If you are sloppy and confused and do not look
>   carefully at your observations and conclusions _regularly_, you are not a
>   person with whom this process can be expected to produces good results.

Who tells you I'm not practicing it on a daily basis?

>   I am looking forward to how well you understand these premises of a
>   discussion at the level you seem to seek.  I think it is just as much

I hope I'm not doing too bad.

>   pretense and hogwash as claims to live in a world of "proofs", which is
>   also only for show to people who do not think it through.

One has to recognize that a lot of our daily activities consists of
building models and executing "proofs" in the model by constantly
verifying it against the real world.

I currently enjoy seeing my two year old son grow and learn.  It takes
kids awhile until they figure out the concept of object permanence:
objects are still there even if you close your eyes.  Then they have a
lot of fun executing some proofs in the form of dad hiding and
reappearing behind a curtain.

I bet the higher thought processes of animals are alot like that.
What separates us from animals is that we have consciousness, and are
able to use it in order to recognize that a model is a model and act
appropriately.

There are some things we cannot understand using the model-building
process, consciousness itself is an instance.  This is where the world
of models, rules and proofs fails, and where psychology, philosophy
and religion come into play.  That does not make these things
irrelevant.

> | It's Yin and Yang.  I can only establish facts about how important an
> | argument is to someone by trying to push them.  It is polite to keep
> | that push as small as possible, and a strong reaction to a small push
> | indicates a big force not originating from me.
>   This presupposes that there is a priori and universal agreement on the
>   amount of push -- that I cannot think your push was bigger than you think
>   it was.

I can only tell you about my intention.  I didn't consider discussion
of language features a major flame bait, but as a good opportunity to
either learn or teach (and I am open for both directions).

Of course, we both can only see the combined result of our forces.
Judging by the size of the thread and the number of words written, it
was a big force.  Maybe we can do something useful with it, if we can
cooperate to direct it.

>   Since this is obviously ridiculous to base an argument on, what
>   such a reaction _really_ indicates is most probably that you have failed
>   to assess the amount of push you exerted correctly, and particularly so
>   because you failed to understand that you relied on an agreement that
>   simply _could_ not exist, for your argument to be true.  Such sloppiness

My assertion might have failed because I didn't have the knowledge
that I was here to seek.  And an agreement might not exist (yet)
personally with you, but I have reason, based on my experience with
selected members of this community (personal, and reading their source
code and documents), to believe that I would find people who agree
here.

>   in thinking that pretends to be logical is actually quite alarming, as it
>   indicates that you have never been challenged on its fundementals and
>   have been allowed to walk through life thinking much too highly of your
>   logical abilities and the guaranteed results of applied logic.  This is
>   almost like watching old Star Trek episodes with the ridiculous role of
>   Spock, who is "logical" based on a bunch of ludicrous premises.

Your irrational behaviour is a living proof that logic has it's limits.

>   The lack of precision and willingness to think through what you are
>   saying is downright annoying.  You think too little and talk too much.
>   Nice words, looks good to the careless observer, but is just bullshit.

You're welcome to actually show where my logic is flawed, instead of
just claiming it's bullshit.  Maybe I learn something.  Maybe you
learn something.  Are you prepared for both?

>   You simply fail to understand that people do not just disagree on some
>   surface issue -- they may disagree all the way down.  Even if you seem to

I do not fail to understand this, although two persons who disagree on
*anything* are rather unlikely.  What you fail to understand is that
this isn't the case between the Lisp and the Dylan folks, for they
have common roots.

>   People can likewise agree on some "Lispness" of their pet languages, but
>   strongly disagree that a language that lacks s-expressions in its syntax
>   should even pretend to be "a Lisp".

That probably depends on the angle of view.  For me, adding an
s-expression parser to the Gwydion Dylan compiler looks like a project
I could pull off if I dedicate a month or two, whereas removing
dynamic typing from Dylan is something I'd consider impossible for
myself, and changing the heart of the language.

So on the worktime-for-Andreas-metric, Dylan is two months away from
anything that can pretend to be a Lisp in your metric.

Wether that's still a Lisp on your metric is of course up to your
call, but I'd argue that it's close, the roots are common, and a
discussion here fruitful.

> | If you consider it advertising when I'm saying that Dylan was a good
> | idea, then yes, I am advertising.  But it's honest, since that's my
> | opinion that I can back with arguments, and I can be convinced otherwise
> | with better arguments.
> 
>   What utter nonsense.  You decided on what made you choose Dylan long
>   before you ever heard any "argument" either way.  You will not be swayed
>   on any but the most superficial points by arguments.  You will, instead,
>   protect yourself from such swaying.  How can I say this so certainly?
>   Because you show an amazing lack of insight into how people choose and
>   value things.  Of course, now that I have said this, you may think about
>   it and you may decide to surprise me.  That would be kind of fun.

I am observing how people choose languages.  Rest assured that
s-expressions are the number one reason why people shun Common Lisp,
regardless of whether they are good, bad or meaningless.

Since you seem to have bigger insight into how people choose and value
things, you might want to share it with us, instead of calling people
names.

Anyways, even if your assertion about my lack of insight were true, it
still wouldn't say anything about the result of arguments on my
points.

> | I do not mean to flame, troll, or insult people.  I'm coming here with an
> | open mind, and a story to tell.
>   You would like to believe so, but it is in fact false.
> 
>   If you react _defensively_ to the last line, your mind is _not_ open.

Why should I react offensively?  Although I cannot be sure of the
causes of my actions, as they depend on my environment, I am the
ultimate authority on my intentions.  You have no chance of
questioning that without at least trying to support it with evidence.

So your line is obviously offensive, attacking my integrity without
backing it up.  By not being offensive, your attack runs into
nothingness, and you lose balance.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Lieven Marchand
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <m34rnetyq7.fsf@localhost.localdomain>
Andreas Bogk <·······@andreas.org> writes:

> By the way, please forgive the use of the Dylanesque empty?.  I'm so
> used to working in a language where I can express operations on
> collections independent of their implementation that I completely
> missed the fact that there is no empty? in Common Lisp, and that it
> can't be implemented in a way that would have equal performance to
> (when foo).

It probably can within a small constant amount and worrying about such
trivia isn't productive. Please do not set up such strawmen.

> Do you consider yourself to be that smart?  How deeply have you looked
> into Dylan, for instance, to be able to say that it doesn't have the
> Lisp nature?

You come to argue Dylan in c.l.l. and ask people here to prove their
Dylan credentials? (For the record, I have the Apple infix Dylan book
floating somewhere about but lost intrest when the Dylan designers
introduced misfix. You're paying the price now with your overcomplex
and underpowered macro system)

-- 
Lieven Marchand <···@wyrd.be>
She says, "Honey, you're a Bastard of great proportion."
He says, "Darling, I plead guilty to that sin."
Cowboy Junkies -- A few simple words
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87667t9fex.fsf@teonanacatl.andreas.org>
Lieven Marchand <···@wyrd.be> writes:

> > By the way, please forgive the use of the Dylanesque empty?.  I'm so
> > used to working in a language where I can express operations on
> > collections independent of their implementation that I completely
> > missed the fact that there is no empty? in Common Lisp, and that it
> > can't be implemented in a way that would have equal performance to
> > (when foo).
> It probably can within a small constant amount and worrying about such
> trivia isn't productive. Please do not set up such strawmen.

I am sorry, I guess I have been discussing with Erik too long and
stared adopting his style of discussion.

> > Do you consider yourself to be that smart?  How deeply have you looked
> > into Dylan, for instance, to be able to say that it doesn't have the
> > Lisp nature?
> You come to argue Dylan in c.l.l. and ask people here to prove their
> Dylan credentials?

No, I was specifically addressing Erik, because on one hand he claimed
one cannot say anything about a programming language without having
studied it for several years, and on the other hand he's pretty
certain in his claims about that language.

> (For the record, I have the Apple infix Dylan book
> floating somewhere about but lost intrest when the Dylan designers
> introduced misfix. You're paying the price now with your overcomplex
> and underpowered macro system)

It doesn't feel any more complex than the CL macro system to me.  The
only aspect of "underpoweredness" that I am aware of are procedural
macros, and they are certainly implementable.  If you know more,
please let me know.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3216078922614911@naggum.net>
* Andreas Bogk
| I am sorry, I guess I have been discussing with Erik too long and stared
| adopting his style of discussion.

  No, you are just being yourself, but you are starting to lose control,
  and this need to blame someone else for your problems is quite typical.
  If it really is so easy to make you do thing which you will later claim
  is against your conscious will, I think you should now return to whoever
  told you to come to comp.lang.lisp to post your idiotic drivel, and ask
  for more money or whatever.  It is time for you Dylan retards to quit the
  game-playing you engage in.  Dylan is the language of choice for retards,
  as has been demonstrated beyond all possible doubt.  You have done your
  job, so go home, now.

| No, I was specifically addressing Erik, because on one hand he claimed
| one cannot say anything about a programming language without having
| studied it for several years, and on the other hand he's pretty certain
| in his claims about that language.

  Your reading comprehension has been questioned several times, already, so
  why do you need to prove that you are so amazingly unintelligent?  Note
  that this is no longer a question about your stupidity, which is a choice
  not to think.  You really are retarded.  It is impossible to want to fake
  your behavior if you had the intelligence to do anything better.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Lieven Marchand
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <m3bshkrz9d.fsf@localhost.localdomain>
Andreas Bogk <·······@andreas.org> writes:

> It doesn't feel any more complex than the CL macro system to me.  The
> only aspect of "underpoweredness" that I am aware of are procedural
> macros, and they are certainly implementable.  If you know more,
> please let me know.

One line definition of CL DEFMACRO: You get the forms as lists of
symbols and you write a function that returns Lisp code in the form of
a list of symbols. (This neglects automatic DESTRUCTURING-BIND and a
few other niceties but it will do for a discussion).

It's a simple model that leaves the programmer the choice to be
hygienic or not, what cases to support or not, etc. Dylan's macros
have a lot more hair to deal with the misfix syntax, have an ugly hack
to allow variable capture and still aren't powerful enough in practice
to write something like LOOP, let alone SERIES.

Bruce Hoult and I had that argument a year or two ago. You'll likely
find it at groups.google.com.

-- 
Lieven Marchand <···@wyrd.be>
She says, "Honey, you're a Bastard of great proportion."
He says, "Darling, I plead guilty to that sin."
Cowboy Junkies -- A few simple words
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-BDCFAD.16583901122001@news.paradise.net.nz>
In article <··············@localhost.localdomain>, Lieven Marchand 
<···@wyrd.be> wrote:

> It's a simple model that leaves the programmer the choice to be
> hygienic or not, what cases to support or not, etc. Dylan's macros
> have a lot more hair to deal with the misfix syntax, have an ugly hack
> to allow variable capture and still aren't powerful enough in practice
> to write something like LOOP, let alone SERIES.

Since the Dylan "for" loop is pretty much isomorphic to CL's "LOOP", and 
Dylan's "for" is implemented as a macro, that claim would appear to be 
false.

I haven't had a chance to look closely at SERIES.  I downloaded it and 
it's *enormous*!!

-- Bruce
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215994770887944@naggum.net>
[ I have made an effort to answer with a one-liner to each paragraph, with
  further elaboration following it.  You may skip the elaboration unless
  you want to respond to this. ]

* Andreas Bogk
| Well, it extends to a general dislike against any use of inband
| signalling in a lot of other contexts.

  Where did this "dislike" come from?  When does your "dislike" begin?

  I would have assumed that you dislike everything that computers do with
  that attitude, since they practically _embody_ the principle of inband
  signalling these days.  Digital transmissions practically _forbid_ real
  out-of-band signalling -- it is all done by in-stream encapsulations and
  encapsulation these days, precisely what "in-band" refers to.  Sheesh.

| This is based on observation of the problems (especially security
| problems) of software that violates these rules.

  Ah, the good old argument from "my experiences of fear and pain", again!

  The best solution to some people's severe personal problems with all
  things painful is simply to ask them to increase their pain threshold --
  nothing else will actually help.  Wimps and whiners will never amount to
  anything in a world where the expectation that everything be painless is
  routinely disproved.  An experience of pain means that _you_ do something
  wrong.  If you are the arrogant type, you will blame somebody else for it
  or the universe in general if you are _real_ idiot, but arguments based
  on "it hurts, so I won't do it" are actually _wrong_.  It was _not_ what
  you did that made it hurt, except in such trivial cases that you never
  talk about it.

  If you design crappy software and something dies on you, the cause is not
  because the language violated some stupid rule of in-band signalling --
  it your own, personal ineptitude that was the cause and your own goddamn
  fault for not being able to deal with it when you implied to yourself and
  the computer and your superiors that you could.

| So anybody who thinks that CL is better off violating this rule either
| doesn't believe in it, or believes that there are more important rules.
| In both cases, I am curious to know why.

  Or they do not actually violate it, because you are simply _wrong_.

  Your failure to grasp what you want to accuse others of is repeated with
  an alarmingly high frequency, and it seems to be increasing rapidly when
  you are chastised for it.  The world is not at fault for not obeying your
  rules.  You _really_ need to grasp this.  Rebellious idiot students could
  perhaps get away with such cluelessness in the late 1960's, but rebelling
  against the authority of a programming language standard is simply _nuts_.

> As a matter of fact, (when foo ...) has a _much_ lower cognitive load
> than (unless (empty? foo) ...).

| Only if you have interned this particular feature so much that you also
| see the latter meaning if you see the former in code.

  You _know_ this kind of thing?  You show no evidence of doing so.

  This is stuff that is _measurable_ and which has been studied over and
  over.  "Cognitive load" is actually a well-known phenomenon, and it is
  one of those things for which ignorant newbies are _not_ the standard by
  which everything is measured.  When I said "as a matter of fact", I did
  not mean your kind of fact, I meant _fact_.  Do you understand this?

  I also demonstrated that (empty? foo) is the _wrong_ replacement, that
  empty? must be true of much more than lists, but that none of these are
  false.  In other words, you are just _wrong_.

  People who are psychologically prevented from accepting anything that
  other people tell them is the rules they have to follow, will get upset
  for no reason about _their_ "rules" being violated.  This is _curable_,
  but not by changing the rules in long established standards.

| Using the former when meaning the latter fails to communicate the intent.

  The former means that one is testing for a non-nil value.

  You are testing for "a non-empty something".  You have misunderstood the
  intent and this causes you to communicate something else.  Most of your
  conclusions come from making similar mistakes and not listening when
  people tell you to pause and think.  This makes you look _tremendously_
  retarded to those who _do_ know.

> If you at _least_ had rewritten it as (when (pair? foo) ...), you might
> have a fighting chance, but the two are not quite similar -- foo could be
> a non-list, in which case empty? might provide the wrong answer.  An
> empty string or vector or hashtable or package or whatever is true in
> Common Lisp, but empty? should be true of all of these.
 
| The intent when writing such code is indeed testing for an empty
| container, so the fact that it works correctly for non-list container is
| a good thing.

  This is actually wrong in Common Lisp.

  It might be right in Dylan, but it goes to show how Dylan is _not_ a
  Lisp, that you are not discussing this in the proper forum, and that you
  are not listening when people talk to you.  If nothing else, this alone
  makes you stand out like a prize moron.

| Too bad this isn't true for the (when foo) case, it only works for lists.

  You demonstrate only your arrogance from ignorance

  I am a little amazed at your lack of will or ability to introspect.  You
  are reacting in a way that demonstrates that you do not listen at all,
  but react only to what your "impressions" tell you is happening.  This is
  the modus operandi of prejudicial _idiots_.

| By the way, please forgive the use of the Dylanesque empty?.  I'm so used
| to working in a language where I can express operations on collections
| independent of their implementation that I completely missed the fact
| that there is no empty? in Common Lisp, and that it can't be implemented
| in a way that would have equal performance to (when foo).

  Yes, paying attention is evidently too high a price for your arguments.

  Maybe you will pay more attention in the future?  That would really help.

> I see a person who thinks _much_ too highly of his own abilities.

| I've been to some meetings of standardization groups, and have seen how
| they work, thank you.  Their compromises are often not mine, and their
| documents below the standard of the individual members.

  Why go to such lengths to confirm what I just said about you?

  Why do you think your extraordinary ability to generalize from painful
  experiences produces _true_ or _useful_ results?  You do not even seem
  able to recognize that having been to "some meetings" does not give you a
  right to conclude _anything_.  This implies that you think the painful is
  the normal, and that there is nothing you can or should do about it.  And
  that explains why you dig yourself in deeper all the time, too.

  Part of the ability to generalize correctly is the ability to weed out
  exceptional situations and not confuse noise and signal.  If you think
  what you have observed gives you grounds to believe it is the _normal_
  situations, you are as mistaken as you are about this forum.  You simply
  do not get normal reactions when you poke people in the eye, and you
  _should_ be able to understand this.  However, I doubt that you are.

| I've only been using programming languages for the last 14 years, and
| I've only been studying programming language design for the last 5 years,
| so I'm certainly neither the most experienced language designer nor the
| best.

  Yet such incredible immaturity after so much experience is _alarming_.

> E.g., I know a lot of people who are better than me at many of the things
> I want to be good at, but I know far, far more people who only _think_
> they are and who have yet to wake up and smell the coffee and realize
> their "ranking".

| So your participation in this newsgroup has the purpose of establishing
| some smartness ranking?

  No.  Reading comprehension is not your strong suit, is it?

  Does your dysfunctional brain realize that as you go wrong with such a
  mindless accusation, you need to try something else, or will you just
  think you have proved your argument _because_ I deny it?  Really stupid
  people tend to consider their prejudices proved the stronger their victim
  objects, proved when the victim does not object, and proved when they
  agree.  That is what stupid prejudice is all about.  You sound like one
  who suffers from this particular problem and post your stupid prejudice
  because you think this will win a debate for you, when what _would_ have
  helped is simply using your goddamn brain to _THINK_.

  Smart people recognize other smart people.  Stupid people do not.  This
  means that failing to understand one's "ranking" is an indication that
  one is stupid below an important threshold.  Your persistent failure to
  read what people write accurately, however, is a pretty good sign you are
  a very unobservant person in general.

> These latter people tend to hate me for not allowing
> them to keep thinking they are far better than they are.

| I think most people tend to hate you because of your attitude.

  You are not most people, nor do "most people" hate me, you dipshit.

  That you are not most poeple _should_ be an important realization for
  you.  You cannot extrapolate your experiences to other people, not in
  normal situations, and especially not in abnormal situations.  Every
  argument that appeals to statistics about what other people think are
  ipso facto _invalid_ and merely tells others that you are immensely
  stupid.  But you will not understand this, either, will you?

  You reject arguments that appeal to authority, but you appeal to your own
  unverifiable experiences, to fear and pain, and to popularity, all of
  which are incredibly stupid compared to appeals to accept an _actual_
  authority in a particular field.  If you have never been castigated for
  your stupidity before, and if you are in fact as stupid as I think you
  are, you will not understand or accept that you are wrong in any way, and
  you will cocoon yourself in self-preserving delusions that you are not
  acting like a moron here.  My attitude is simply that I despise stupidity
  in all its shapes and forms.  If you want to be stupid, you will hate me.
  If you can figure out that you need to pull yourself together and stop
  making stupid mistakes and arguments, you will _not_ take it personally,
  but _understand_ what the fuss is all about.  I use this as a means of
  determining whether people ar worth listening to after they had a chance.

| I have met people smarter *and* more humble than you.

  I actually doubt that, or you would have recognized that you are being
  castigated for your serious _lack_ of humility in this forum.  Your
  ignorant arrogance and your lack of willingness to listen when people
  reject your premises and tell you that you need to _acknowledge_ the new
  community you have just walked into have all caused you to become more
  and more arrogant -- those are not smart reactions.  And just because you
  think you have "a Lisp" and thus a "right" to post bullshit here does not
  mean anyone has to agree with you.  You have comp.lang.dylan, but it is
  not possible for you to invite people over to your forum to talk with you
  there, is it?  My guess -- nobody _wants_ to.  So you have to trespass on
  their grounds and annoy them on home turf, instead.  Goddamn stalker!

  That you do not at _all_ understand that you are not welcome to post
  bullshit, and that is not just my reaction, means that you are here on a
  mission, where ignoring other people's concerns are perfectly acceptable.
  This is evident in much of what you post.  Such arrogance does not make
  people likely to think you are here to be constructive or learn something.

  Considering that you appeal to logic, but demonstrate no skills in using
  it even to save yourself, I consider the rest of your attempts to look
  friendly and polite be deceptive as well.

| It's not irrelevant, it's called "learning".  It might even be of some
| use if I ever decide it would be nice to design a new language from
| scratch.

  Learning?  Learning _what_?

  That being an obnoxious idiot tourist in a new community makes people
  pissed because you are too goddamn stupid to look around you and wait
  until you grasp what is going on before you start to make "suggestions"
  for that community to adopt?

  That some people do _not_ consider what you are unable to deal with
  errors, and would in fact do the exactly same thing all over again?

  That some people _like_ what you have such a personal problem with?

  That nobody cares what a goddamn Dylan freak has problems with?

| But I think slightly improving existing languages is a more realistic
| target.

  It does not happen the way you think.

  Waltzing into a community to tell people how to improve _must_ fail,
  especially when you come from a community that walked out on Lisp in the
  first place to do their stupid thing.

  That you already think standards committees do poor work and that you
  "know" how they work (thank you), must mean that you are here to make
  people _abandon_ their standard and adopt Bogk Lisp, instead, which would
  of course be an improvement over absolutely anything, right?  Now, we
  just had another case here with a guy who just could _not_ accept that
  Common Lisp has a large set of perfectly fine conditionals -- he just
  _had_ to use his own, and anyone who uses the standard ones around him
  gets chastised for it and have their code mutilated.  He, too, has a very
  strong disdain for "committee work".  He, too, knows best himself.  There
  is a commonality here that you may not notice right away, so let me make
  it clear to you: The reason people who have "special ideas" do not get
  them accepted is that most of the time, it is because they are _nuts_,
  and that their "special ideas" are old ideas that have already been
  discarded or are known to lead into major messes.  Failure to listen to
  the community in this situation means that one is not contributing to the
  community, but regards the community as one's private ego massage team.
  People generally reject every attempt to put them into this role.

  Languages are not slightly improved.

| Do you pay taxes?

  Next moronic question, please!  Geez, just how retarded _are_ you?

| In my view, it's a minor inconvenience that I don't actually mind
| anymore, and probably just a cultural thing.

> "Just a cultural thing"?  That is precisely what the super-tolerant
> idiots say about the molestation of young females in backward cultures
> that claim it is their "religion" that defends this criminal act against
> at least half of humanity.  Cultures are tremendously important, and some
> of them are just plain _bad_.

| Have you just compared infix syntax to child molestation, or is this just
| my imagination?

  Just your hyperactive and free-wheeling imagination, again.

  I also think you missed the reference to female circumcision and thought
  it was about "child molestation" because, again, you had to fill in the
  blanks where you did not understand something fully.  You are _really_
  quite fascinating to watch.  Actually being bothered to be accurate or
  pay attention to your level of comprehension it clearly too much to ask
  of you.  That you have not met people who have told you to go to hell
  previously must be because they have been too polite to tell you the
  truth, and now you are all hysterical because I am "rude" to you.  Get a
  grip on yourself and figure out that only _you_ can change all this.

| I've had several opportunities to demonstrate my technical skills, [...]

  Why are you defending yourself with something so utterly irrelevant?

  Who "you" are is of absolutely no interest to me.  Your arguments and
  opinions are, and only your arguments and opinions.  They are the subject
  of my criticism, not you, but they have a person and a will to act behind
  them, and it is in the capacity that "you" are chastised.  Do something
  else, and I will respond to that, instead.  If you persist in defending
  yourself, I must have been correct in my assessment and made it hurt real
  bad.  You should not expose yourself that much in public.  This is not a
  personal chat forum.

  If you post mostly stupid arguments and nonsense, that is what you are,
  here.  If you never do any better, then it must be because you _cannot_
  do better.  When it hurts to post some moronic bullshit, try something
  different -- do not just _be_ a moron and keep posting moronic bullshit
  because you think you have a "right" to do it.

> To trace the history of how we ended up with our conclusions, ignore all
> the explicit arguments and premises and logic and focus on what went down
> the drain before you even _started_ to think about it.  _That_ is where

| I think that would be a bad approach.  Logic has it's limits, but it
| cannot be plainly rejected as irrelevant.

  Your reading comprehension problem is showing again.

  Can you at least make an _effort_ to think about what you read and
  perhaps fail to make so many stupid mistakes?  Dude, you are a random
  number generator.  How can anyone talk to such a moron as yourself when
  you grasp _nothing_ of what you are being told?

  Logic was not rejected as irrelevant, you moron, you were told to ignore
  it if you wanted to trace the _history_ of your conclusions.  It is your
  tacitly accepted premises that guided everything -- logic made it simply
  follow from those premises.  Your amazing lack of thinking skills is
  beginning to be such a curiosity that I am tempted to reply to you only
  to see if you do any other hilariously funny mental tricks.

| How deeply have you looked into Dylan, for instance, to be able to say
| that it doesn't have the Lisp nature?

  It has rejected s-expressions.

  How deeply would I have had to look into Dylan to satisfy you?  There is
  clear evidence that you would not accept _anything_ as satisfactory.

  You show us that you have not understood what Lisp nature is, because the
  only "Lisp" you _actually_ know well is Dylan.  To you, Common Lisp has
  Dylan nature, but that does not mean that Dylan has Lisp nature.   You do
  not know the first thing about Lisp nature, except for what some other
  Dylan freak has told you about it.  Right?

| You still have to show a serious flaw in my logic.

  Blasting your premises to pieces does not count?

  Must I _accept_ your premises in order to show a weakness in your logic?
  Sorry, but that is not how _real_ logic works.  _Real_ logic ensures that
  conclusions follow from their premises, and that is all.  The best that
  can be done with logic is to show that _if_ the premises are correct,
  _then_ the conclusions also are.  If the premises are false, _anything_
  can follow.  So if you are hung up in logic, which is fairly trivial and
  mechanistic, you need a way to ascertain that your _premises_ are good.
  You do not seem to grasp this at _all_.

  It is utterly amazing to me how anyone can talk so loudly about logic and
  not understand the importance of the premises for his reasoning, and it
  is even more amazing that you _dismiss_ those who reject your premises
  when they are simply _untrue_.  What the hell kind of logic is it that
  you want, Andreas Bogk?

| Who tells you I'm not practicing it on a daily basis?

  Your news articles, you dimwit.  Grow a clue, now.

| I hope I'm not doing too bad.

  No, you are doing a lousy job.

| One has to recognize that a lot of our daily activities consists of
| building models and executing "proofs" in the model by constantly
| verifying it against the real world.

  Really?  And if one does not "recognize" this?

  People who believe in the model bullshit are wrong.

| Then they have a lot of fun executing some proofs in the form of dad
| hiding and reappearing behind a curtain.

  Yeah, I am sure they execute proofs when they figure these things out.

  This means that "proof" to you has a pedestrian meaning and not a formal
  meaning at all.  This is quite informative.  Poor children, by the way.

| I bet the higher thought processes of animals are alot like that.

  Yes, my cat also executes proofs.  Cool, I always thought she was smart.

| There are some things we cannot understand using the model-building
| process, consciousness itself is an instance.  This is where the world of
| models, rules and proofs fails, and where psychology, philosophy and
| religion come into play.

  And just _how_ do you know these things?

  This looks more and more like the same old problem of premises taken for
  granted and which cannot be questioned.  The fact that you reject every
  attempt to question your premises rhymes with your belief that others
  have no rational basis for their conclusions, either, and hence you make
  those stupid accusations about "gospel".  Logic from "postulates" and
  "axioms" and otherwise _unquestioned_ premises is a fool's business --
  damn near _anybody_ can do it, it is a simple matter of following a bunch
  of fairly straightforward rules to the letter.  Figuring out whether the
  core premises are good, however, requires serious skill and deep thought,
  sometimes the work of geniuses.  This is where people usually fail, and
  miserably.  This is where philosphy becomes _interesting_.  Your reaction
  to this is as follows, however.

| That does not make these things irrelevant.

  Your "logic" appears to be based on unquestioned beliefs that have no
  rational basis whatsoever.

| Your irrational behaviour is a living proof that logic has it's limits.

  Do you even read what you are writing?  Do _you_ laugh, too?

  But please let me watch your learning ability in practice.  "It's" is a
  contraction of "it is" or "it has".  "Its" is a possessive pronoun.  Can
  you figure out which to use at what time and consistently avoid making
  more silly mistakes?  That would be appreciated.  I assume, however, that
  you have developed your English, Dyneng or something, in which you have
  your own rules of grammar that are much better than all those stupid ones
  that a very large community of people much less smart than you have made
  the mistake of using for hundreds of years.  You would of course still
  claim it is "an English" because it has "English nature", even though it
  fails to conform to accepted standars for English.  "It's" is clearly the
  best way to express the possessive form of "it".  Of course, consistency
  be damned, so it s not "he's" and "she's" and "they's" and "us's", etc,
  it is only "it's".  The rest of the possisive pronouns are just fine.
  But for someone who confuses these two to carp about the confusion caused
  by nil and false and the empty list is hilariously funny.  To make such a
  stink about disliking in-band signalling and then to abuse the apostrophe
  to destroy whatever information is already there is very, very amusing.

  If it were not for your terribly stuck-up attitude problem and arrogance
  towards communities you are not a member of, I would let your mistakes
  pass -- this is not an English class -- but you are so certain of your
  own perfection that pointing out that you make a grade-schooler's mistake
  in English and are too arrogant to recognize it, becomes important.  You
  do not pay attention to details.  You make mistakes that you _ignore_.
  Then you go all huffing and puffing about lots of things you fail to
  grasp fully.  You are an idiot, Andreas Bogk.  And so are your stupid
  concerns about Common Lisp and Dylan's pretense of being "a Lisp".

| You're welcome to actually show where my logic is flawed, instead of
| just claiming it's bullshit.

  The premises you do not question and want people to agree to, are wrong.

  You do not listen to this at all, but want people to accept them and then
  show you "logical flaws" in your reasoning from them.  This is not how
  logic works.  Logic works only if the premises are known to be true.  If
  your premises are false, logic alone does not produce useful results.  A
  lot of Star Trek fans seem to believe in Spock-style logic.

| I do not fail to understand this, although two persons who disagree on
| *anything* are rather unlikely.

  Did you mean "everything" here or what?

| What you fail to understand is that this isn't the case between the Lisp
| and the Dylan folks, for they have common roots.

  This is one of the premises that you do not want to hear otherwise about.

  No, they do not have common roots, they have _some_ common roots, and so
  do almost all programming languages.  Just as Scheme has more Algol in it
  than Lisp, Dylan chose a syntax that is anything _but_ common with Lisp.
  In other words, Dylan has at least one root that is not common with Lisp.
  So your whole goddamn _premise_ is wrong.  The Dylan community rejected
  the Lisp community, and now you need to get back into the warmth because
  it gets cold and lonely over there in miserably failed Dylan land.  Guess
  what?  You are not welcome back if you want to keep your arrogance and
  your rejection and your stupid little language.  Eat enough crow, make
  enough amends, understand that your language is sufficiently different
  from Lisp that you should really go to Python or Ruby or something if you
  want something that looks and feels the same, and _maybe_ you would not
  be such a goddamn obnoxious tourist.

| For me, adding an s-expression parser to the Gwydion Dylan compiler looks
| like a project I could pull off if I dedicate a month or two, whereas
| removing dynamic typing from Dylan is something I'd consider impossible
| for myself, and changing the heart of the language.

  If you can write your code in the s-expression syntax, that would count.
  If you cannot, then it does not count.  Do you grasp the difference?

| Rest assured that s-expressions are the number one reason why people shun
| Common Lisp, regardless of whether they are good, bad or meaningless.

  Well, gee.  How do you know these things?

  How many real people did you poll to find out, as opposed to imaginary
  duplicates of yourself?  People shun Common Lisp because it does not have
  any of the common names for anything that the C community has chosen.
  What you stupidly and misguidedly call the "learning curve", which is
  really the amount of stuff learned over time, is _accused_ of being
  "steep", which would actuall mean that one can learn a lot of stuff in a
  very short amount of time, which would be _good_ for a language.  What we
  have, instead is that the cost of learning Common Lisp is one of getting
  rid of a _lot_ of old baggage.  The parentheses only symbolize this.
  Only real idiots are _really_ put off by the parentheses, but since it is
  accepted, and it is not accepted to be a moron who cannot learn new
  languages because he simply does not have the brain capacity to learn
  them in time, especially in a culture where people are taught a lot of
  lies about programming languages, such as them all being the same with
  only a little new syntax, people will do a lot of irrational things to
  avoid feeling stupid -- look at yourself and how you react to my pointing
  out that you are doing a lot of stupid things: you get _defensive_ and
  all snotty about "rude behavior", but you do _not_ fix the problem.  This
  means that you would rather be stupid and please, nobody say you are,
  than _not_ be stupid.  People who are unable to come to grips with Lisp
  are the same kind of people as you -- they carp about something that is
  _completely_ irrelevant which gives them a stupid _excuse_ to fail, so
  they do not look so stupid in their own eyes.

  However, only people who are unafraid of making mistakes and failing will
  ever succeed in anything.  Learning anything new means you will make some
  stupid mistakes early that may be hard to fix if people around you are so
  "polite" as not to point them out to you, and if you are unintelligent
  and unobservant, you will not even notice that things no longer make a
  whole lot of sense.  This is the time when smart people stop to think,
  and stupid people start to blame the language.

| Since you seem to have bigger insight into how people choose and value
| things, you might want to share it with us, instead of calling people
| names.

  If you start to focus on what _you_ want, you would see I do _both_.

  Since you _are_ behaving incredibly stupidly with your constant whining,
  and it is the cause of what you do not like, just stop whining.  It is as
  simple as that.  You see, unlike you, I do not criticize something just
  to criticize it.  I do not harrass you about something that you are
  unable to change the way you harrass this community about your perfect
  Dylan that made some other choices.  I _expect_ you to grasp what you are
  being criticized for, and _also_ critize you for it if you do not.

| Anyways, even if your assertion about my lack of insight were true, it
| still wouldn't say anything about the result of arguments on my points.

  OK, if this were literally true, it would mean that you pull your
  arguments out of thin air.  I quite concur with this assessment.

> If you react _defensively_ to the last line, your mind is _not_ open.

| Why should I react offensively?

  Again, reading comprehension is not your strong suit, is it?

  But well, you _did_ react defensively, so I have seen what I need to see
  from you.  Next time, try actually responding to what people _write_, not
  what you read out of your own mind.  Or look up the difference between
  "offense" and "defense" in your favorite dictionary.

  Just stop making so many stupid mistakes.  THINK!

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Kaz Kylheku
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <Nu0N7.385$nm3.56430@news1.rdc1.bc.home.com>
In article <··············@teonanacatl.andreas.org>, Andreas Bogk wrote:
>As a feature, it feels like a convenience hack so you can write 
>(if foo) instead of (unless (empty? foo)).
>
>That's not much of a gain, given that you have just violated the
>design rule of having a way to differentiate between a valid and an
>invalid result. 

In places where the Scheme language report says that the result of an
expression is unspecified, or that an evaluation order is unspecified,
what design rule is being followed?
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87y9krcf5g.fsf@teonanacatl.andreas.org>
···@ashi.footprints.net (Kaz Kylheku) writes:

> In places where the Scheme language report says that the result of an
> expression is unspecified, or that an evaluation order is unspecified,
> what design rule is being followed?

"Leave some freedom to the poor implementors."

I'll refrain from judging this.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwadx7ozzk.fsf@shell01.TheWorld.com>
Andreas Bogk <·······@andreas.org> writes:

> ···@ashi.footprints.net (Kaz Kylheku) writes:
> 
> > In places where the Scheme language report says that the result of an
> > expression is unspecified, or that an evaluation order is unspecified,
> > what design rule is being followed?
> 
> "Leave some freedom to the poor implementors."
> 
> I'll refrain from judging this.

Why are the implementors more deserving of freedom than the users?
Certainly there are more users.  And they do the activity of using much
more often than the implementors do the activity of implementing.

Implementation doesn't need to be easy, just possible.

Indeed, the whole point of an implementation is to centralize hard things
so that they are done only once.  Easy things don't need centralization.

I am one of the "authors" (such as we are) of the Revised Report on
Scheme.  I've participated in the meetings.  The "freedom" is not left
there for implementors, as far as I've ever been able to tell.  The
Scheme designers rarely discussed implementation beyond "is it
possible".  The freedom is there because the designers, as a group at
least, though there are individual exceptions and I like to claim I'm
one of them, have a phobia about the spec being too long, regardless
of whether that makes the spec "more useful".  As to "more useful", we
once had a discussion in the design committee in which some people
hinted that if the spec were more useful, the issue of usefulness
might cause control of the language to be taken from the committee and
put in the hands of users, who had a vested stake in the outcome.
That is, that the usefulness of something causes design principles to
be sacrificed and is the road to disaster.  Further, the committee
has, when it has spoken at all, which isn't much recently, expressed
considerably more interest in the issue of book compatibility than
implementation compatibility.  To put that in the bluntest of terms,
individuals on the committee have sometimes even gone so far as to say
that their focus has been on preserving the right of people who
disagree about how to write Scheme textbooks to assert what they like
without trampling one another.

I think CLTL was a similar stage of language evolution to Scheme.  It
was an attempt to make the words span the gap between differing
implementations, hoping that by leaving enough things unspecified, you
could make a lot of disparate behaviors conforming.  The CL community,
at any rate, decided this was not acceptable, and demanded that things
be made more compatible, that things left unspecified be made possible
to test for, etc.  We could have left things like evaluation order, or
the order of certain class precedence lists in classes created by
DEFCLASS, unspecified.  But that would have just hurt users in the
name of "implementation flexibility".

Language design is not about pleasing implementors.  (Just as "raising
kids" is not about "pleasing parents".)  There is a primary task to be
accomplished which drives, or ought to drive, the goodness of the
result.  Users of a language are not, or ought not be, secondary to
the process.  They are why we have languages.

Whatever one thinks of the NIL/false pun, one can hardly accuse it of
being there for "implementor convenience".  It was put there because some 
users wanted it.  Some of us wish there were more such, not fewer such.
I really like the way it works in MOO, with "", #(), and errors being false, 
too.  I definitely regard that the language would be poorer for my needs
if we moved away from such overlap instead of toward it.  

I also did not start out thinking this.  I used to rant at people
about not doing (NOT (NULL ...)) because various people thought I
should or because it just seemed fun to do.  But someone once pointed
out to me that it's easier to learn to "like" something than it is to
learn to "unlike" something.  I don't know if that's true, but one can
certainly find anecdotal evidence to suggest it might be.  And anyway,
I've come to like what CL does.  I doubt I could as easily come to
unlike it without some major problem coming up with it.  And I've been
programming Lisp relatively intensely for 20+ years without such a
major problem coming up, so I'm starting to doubt that it will.
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87r8qjc856.fsf@teonanacatl.andreas.org>
Kent M Pitman <······@world.std.com> writes:

> > "Leave some freedom to the poor implementors."
> > I'll refrain from judging this.
> Why are the implementors more deserving of freedom than the users?

I'm not implying they do.  But they are deserving the freedom to
actually be able to implement, and to reach a consensus about the
standard if their implementation differ in some detail which would be
hard to change.

I think in a way a designer is a potential implementor, so he's often
in the same position.

> Implementation doesn't need to be easy, just possible.

I agree.  This seems to have been one of the design principles of
Dylan as well.

[lots of stuff I completely agree to snipped]

> Whatever one thinks of the NIL/false pun, one can hardly accuse it of
> being there for "implementor convenience".  It was put there because some 

Nobody said that.

> users wanted it.  Some of us wish there were more such, not fewer such.
> I really like the way it works in MOO, with "", #(), and errors being false, 
> too.  I definitely regard that the language would be poorer for my needs
> if we moved away from such overlap instead of toward it.  

How do you feel about the false-or(<type>) mechanism?  Wouldn't that
just be the generalization of that overlap in a cleaner way?

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwhere7uwc.fsf@shell01.TheWorld.com>
Andreas Bogk <·······@andreas.org> writes:

> > ... I definitely regard that the language would be poorer for my needs
> > if we moved away from such overlap instead of toward it.  
> 
> How do you feel about the false-or(<type>) mechanism?  Wouldn't that
> just be the generalization of that overlap in a cleaner way?

(I reject your implicit suggestion that the word "clean" applies to
one of these approaches and not to the other.  There is nothing "unclean"
about correctly applying any well-defined semantics.  What feels "unclean"
to you, as nearly as I can tell, is that you don't want the definition 
to be what the definition is.  But the language is defined as it is,
and since it's in no danger of changing, there is nothing unclean
about the use.)

But in answer to your question, no, the (FALSE-OR type) thing moves
in the wrong direction.  It IS a useful technology for places where it
was not possible to find a degenerate element within the set.

For example, had () and NIL and #f been all separate to start, I could
imagine arguing to make () false, just as I have noted that I'd be
happy if "" was false and #() was false.  However, I can't imagine
that a priori, I'd argue that (intern "NIL") should result in a false
value.  Absent history, I can't make a huge case that any given symbol
should be false.  So in a world where those were split, and where I
had no memory of this world, I think I'd argue that (FALSE-OR SYMBOL)
was the right way to talk about the union of boolean false and the
symbols, since the choice of any one symbol as a degenerate case
(absent a historical basis, as with Lisp) would be unfair in
Internationalization terms, if nothing else.  And certainly if I were
telling you to merge a faluse value with some random number seed, I
wouldn't try to figure out what a degenerate seed was so that I could
argue it should be false.  I'd just say (FALSE-OR RANDOM-STATE).

But there are places where there are natural nulls, and lists and
arrays (including, of course, strings) are among them.  I don't feel a
need for an extra type in a great many situations.  This is evident in
the number of applications that do (PUSH X (GETHASH A B)) where they
don't check to see if (GETHASH A B) returns NIL, NIL or NIL, T because
it doesn't matter to them.  Good language design is not done by
randomly changing a feature but by doing feature changes in
coordinated sets. So if we could declare a hash table of integers,
there might be cases where people usefully did (INCF (GETHASH A B))
without having to initialize (GETHASH A B) because they would know
that (GETHASH A B) would return 0, NIL when there was no element or 0,
T when an element had been set to 0.

Also, in languages where you have more than one false, you can choose
to do (EQ value 'particular-false-value) and to treat the other values
differently.  So you might want the type (AND (MEMBER NIL) type)
even though (FALSE-OR type) might mean the same thing.  It wouldn't 
capture the intent I'm looking for.   

Keep in mind that in mixed data, the pun problem exists ANYWAY because
a lot of the time I'm making FOO's and representing them somehow. e.g.,
maybe as a standard class.  In that case, NIL can mean absence of FOO.
I can always safely do (gethash 'x *foo-table*) and test the result for
truth because I know there is no false-value in that table.  But suppose,
you say, a FOO is represented as a list.  Yes, then I have to worry the
list might be NIL, and a probelm might result.  SO I say back, suppose
a FOO is represented as a boolean.  (That would mean I only ever have 
two of them.  Or maybe I have some special reason that booleans are enough.
Streams are like this, with terminal I/O and standard-input/standard-output
getting booleans that "represent" them as designators in Lisp.)  Confusion
CAN still result and having the datatypes laid out a certain way doesn't
make the world "clean", it just makes it "less error-prone".  It is all
just a matter of degree, not a binary matter of "good" and "bad".
And even as to degree, moving it in the direction of separation means
more typing for people, and some people seem to regard that as "good"
while others don't, so even the directionality is up for grabs.
From: Marco Antoniotti
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <y6c1yiiyeoy.fsf@octagon.mrl.nyu.edu>
This discussion made me wonder about the status of ASSOC and FIND, and
what would mean to "change the standard".

CLHS reports:

find item sequence &key from-end test test-not start end key => element
assoc item alist &key key test test-not => entry
gethash key hash-table &optional default => value, present-p

Do you think it would be too much of a change to request the
vendors/implementors to change the behavior of the implementation in
such a way that

find item sequence &key from-end test test-not start end key default => element, present-p
assoc item alist &key key test test-not default => entry, present-p

(Of course a better writeup is necessary).

Also, what could be an "agreed upon and simple" machinery such that
all the implementations could check for this "extension"?

Cheers

-- 
Marco Antoniotti ========================================================
NYU Courant Bioinformatics Group        tel. +1 - 212 - 998 3488
719 Broadway 12th Floor                 fax  +1 - 212 - 995 4122
New York, NY 10003, USA                 http://bioinformatics.cat.nyu.edu
                    "Hello New York! We'll do what we can!"
                           Bill Murray in `Ghostbusters'.
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215959457909098@naggum.net>
* Marco Antoniotti
| Also, what could be an "agreed upon and simple" machinery such that
| all the implementations could check for this "extension"?

  I think a new package named COMMON-LISP-2002, say, which implements the
  new symbols and semantics, would be the way to go.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Lieven Marchand
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <m3itbu7te8.fsf@localhost.localdomain>
Kent M Pitman <······@world.std.com> writes:

> So if we could declare a hash table of integers, there might be
> cases where people usefully did (INCF (GETHASH A B)) without having
> to initialize (GETHASH A B) because they would know that (GETHASH A
> B) would return 0, NIL when there was no element or 0, T when an
> element had been set to 0.

I've been using (INCF (GETHASH A B 0)) for that.

-- 
Lieven Marchand <···@wyrd.be>
She says, "Honey, you're a Bastard of great proportion."
He says, "Darling, I plead guilty to that sin."
Cowboy Junkies -- A few simple words
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwy9kqda07.fsf@shell01.TheWorld.com>
Erik Naggum <····@naggum.net> writes:

> * Marco Antoniotti
> | Also, what could be an "agreed upon and simple" machinery such that
> | all the implementations could check for this "extension"?
> 
>   I think a new package named COMMON-LISP-2002, say, which implements the
>   new symbols and semantics, would be the way to go.

Right.  Don't underestimate the number of possible places where an
extra value would fall through and not be wanted.  Changes like this
are "less likely" to break things, but not "unable" to break things.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-092698.12351429112001@news.paradise.net.nz>
In article <···············@shell01.TheWorld.com>, Kent M Pitman 
<······@world.std.com> wrote:

> So if we could declare a hash table of integers,
> there might be cases where people usefully did (INCF (GETHASH A B))
> without having to initialize (GETHASH A B) because they would know
> that (GETHASH A B) would return 0, NIL when there was no element 
> or 0,T when an element had been set to 0.

This is certainly handy in keeping many Perl programs short, but I feel 
that it's not a good thing in a language in which you can implement 
powerful abstractions efficiently.

Your hash of integers is presumably the concrete implementation of some 
abstraction.  This implementation might some day change as you realize 
that another implementation technique has better characteristics.  So 
you don't want to have client code explicitly depending on the 
representation.

There is also no reason to suppose that 0 is always the appropriate 
default value for a numeric value -- that depends on the abstraction 
being modelled, and perhaps on considerations such as minimizing storage 
usage by avoiding explicitly storing data for the most common case.


What I would do is to write a getter and setter that do the right thing 
for the domain being modelled, and get them hooked into the 
GET-SETF-EXPANSION mechanism.  The getter might be as simple as 
element(a, b, default: 0).

-- Bruce
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87herd9i24.fsf@teonanacatl.andreas.org>
Kent M Pitman <······@world.std.com> writes:

> > How do you feel about the false-or(<type>) mechanism?  Wouldn't that
> > just be the generalization of that overlap in a cleaner way?
> (I reject your implicit suggestion that the word "clean" applies to
> one of these approaches and not to the other.  There is nothing "unclean"
> about correctly applying any well-defined semantics.  What feels "unclean"
> to you, as nearly as I can tell, is that you don't want the definition 
> to be what the definition is.  But the language is defined as it is,
> and since it's in no danger of changing, there is nothing unclean
> about the use.)

I think that the point that Common Lisp cannot be changed and would be
worse with that change is well taken.  I can also see nothing unclean
in making use of this feature, given that it is in the design.

As you have correctly asserted, my question was directed at finding
out what approach would appeal to you more, given you were involved in
designing some Lisp-like language without any constraints like
existing code that needs to be ported.

> But in answer to your question, no, the (FALSE-OR type) thing moves
> in the wrong direction.  It IS a useful technology for places where it
> was not possible to find a degenerate element within the set.

Can I understand this answer as saying that making natural nulls false
and using false-or are two techniques addressing the same issue, where
the former applies to less cases, but is better suited to them?

The two approaches seem mutually exclusive to me, though.  Once your
type has an instance that is false, (FALSE-OR type) becomes useless in
that it doesn't behave like a naive user would expect.

> For example, had () and NIL and #f been all separate to start, I could
> imagine arguing to make () false, just as I have noted that I'd be
> happy if "" was false and #() was false.  However, I can't imagine

If I understand it correctly, people argue that the equality of NIL
and the empty list is elegant, because any function returning false
for whatever reason still returns a valid list.  Wouldn't introducing
multiple falses bear the risk of getting a false of the wrong type
where you don't expect it?  For the records, while I haven't written
anything bigger than ten lines in MOO, I never experienced a problem
of that nature.

/When/ introducing multiple falses, I'd argue for introducing a
canonical false as well.

> Internationalization terms, if nothing else.  And certainly if I were
> telling you to merge a faluse value with some random number seed, I
> wouldn't try to figure out what a degenerate seed was so that I could
> argue it should be false.  I'd just say (FALSE-OR RANDOM-STATE).

I think we can safely say that we agree on this one.

> But there are places where there are natural nulls, and lists and
> arrays (including, of course, strings) are among them.  I don't feel a

From your example below, I conclude this should also be true for
integers.

> need for an extra type in a great many situations.  This is evident in
> the number of applications that do (PUSH X (GETHASH A B)) where they
> don't check to see if (GETHASH A B) returns NIL, NIL or NIL, T because
> it doesn't matter to them. 

The price to pay for not having it would be having to write: 

  (PUSH X (GETHASH A B :DEFAULT NIL))

although one could argue that this makes the intent "I know what to do
when I don't find the element" better visible to the reader.

> Good language design is not done by randomly changing a feature but
> by doing feature changes in coordinated sets.

I agree.  The poem mentioned in this thread shows nicely how a random
feature change that looks innocent enough results in an unusable
language.

Before this discussion, I was also unaware of the fact that separating
false and the empty list in Dylan wouldn't work so smoothly if it
hadn't been for type unions and the default keyword in the ELEMENT
function.

> So if we could declare a hash table of integers,
> there might be cases where people usefully did (INCF (GETHASH A B))
> without having to initialize (GETHASH A B) because they would know
> that (GETHASH A B) would return 0, NIL when there was no element or 0,
> T when an element had been set to 0.

Again, 

  (INCF (GETHASH A B :DEFAULT 0))

would have the same effect, with the same consequences on
communicating the intent.

> Also, in languages where you have more than one false, you can choose
> to do (EQ value 'particular-false-value) and to treat the other values
> differently.

That's true.  It's probably the same overhead as having to write
(NULL? value) in languages where the null values aren't false.

This probably reduces the question of which is "better" to the
question of "what case arises more often", and this is so dependent on
style and personal preferences that no answer can be given.

> list might be NIL, and a probelm might result.  SO I say back, suppose
> a FOO is represented as a boolean.  (That would mean I only ever have 

Yes, in case FOO can be a boolean all is lost, and you have to find
another trick.  In Dylan code, one often finds idioms like this:

define constant $not-supplied = pair(#f, #f);

define method foo(bar, #key baz = $not-supplied)
 ...
end;

Unsupplied keyword arguments default to #f.  The purpose of this idiom
is to differentiate between an unsupplied argument, and #f being
supplied to the function.  When not supplying and supplying #f are
semantically the same, the trick is not needed.

$not-supplied is some random object on the heap that's only equal to
itself, and not exported from the module.  So there's no way that
outside code can call this function and pass $not-supplied.

> And even as to degree, moving it in the direction of separation means
> more typing for people, and some people seem to regard that as "good"
> while others don't, so even the directionality is up for grabs.

Requiring more typing is not a a good thing per se.  Separating
semantically what is separate conceptually is a good thing.  Making
life easy for a programmer is a good thing too.  The two often move in
different directions, and the right balance is certainly a matter of
personal taste.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Marco Antoniotti
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <y6c3d2ws5rx.fsf@octagon.mrl.nyu.edu>
Andreas Bogk <·······@andreas.org> writes:

> KMP:
> 
> > need for an extra type in a great many situations.  This is evident in
> > the number of applications that do (PUSH X (GETHASH A B)) where they
> > don't check to see if (GETHASH A B) returns NIL, NIL or NIL, T because
> > it doesn't matter to them. 
> 
> The price to pay for not having it would be having to write: 
> 
>   (PUSH X (GETHASH A B :DEFAULT NIL))

Please note that the above is not correct and that 

	(push x (gethash a b))

is equivalent to

	(push x (gethash a b nil))


> Again, 
> 
>   (INCF (GETHASH A B :DEFAULT 0))
> 
> would have the same effect, with the same consequences on
> communicating the intent.

The correct CL is

	(incf (gethash a b 0))

Cheers

-- 
Marco Antoniotti ========================================================
NYU Courant Bioinformatics Group        tel. +1 - 212 - 998 3488
719 Broadway 12th Floor                 fax  +1 - 212 - 995 4122
New York, NY 10003, USA                 http://bioinformatics.cat.nyu.edu
                    "Hello New York! We'll do what we can!"
                           Bill Murray in `Ghostbusters'.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-C37EC3.16152930112001@news.paradise.net.nz>
In article <··············@teonanacatl.andreas.org>, Andreas Bogk 
<·······@andreas.org> wrote:

> Before this discussion, I was also unaware of the fact that separating
> false and the empty list in Dylan wouldn't work so smoothly if it
> hadn't been for type unions and the default keyword in the ELEMENT
> function.

I think type unions are an *extremely* important language feature, and 
one I miss greatly in C++ & Java.  They allow you to do OO kinda stuff 
without requiring things to have a common base class.  In fact, if I 
understand it properly, the ML languages effectively use type-union 
*instead* of inheritance.  In ML you pick them apart with pattern 
matching, but I think instead combining them with Generic Functions is 
just as good, or better.

-- Bruce
From: Marco Antoniotti
Subject: *ML style Union Types [Re: On nil qua false]
Date: 
Message-ID: <y6czo54qqtx.fsf_-_@octagon.mrl.nyu.edu>
I think this is an interesting concept, and I know that it is one of
the things the *ML crowd uses a lot (IMHO almost as an alternative to
macro processing).

Any idea about how to render them in CL (if possible)?

Cheers

Bruce Hoult <·····@hoult.org> writes:

> In article <··············@teonanacatl.andreas.org>, Andreas Bogk 
> <·······@andreas.org> wrote:
> 
> > Before this discussion, I was also unaware of the fact that separating
> > false and the empty list in Dylan wouldn't work so smoothly if it
> > hadn't been for type unions and the default keyword in the ELEMENT
> > function.
> 
> I think type unions are an *extremely* important language feature, and 
> one I miss greatly in C++ & Java.  They allow you to do OO kinda stuff 
> without requiring things to have a common base class.  In fact, if I 
> understand it properly, the ML languages effectively use type-union 
> *instead* of inheritance.  In ML you pick them apart with pattern 
> matching, but I think instead combining them with Generic Functions is 
> just as good, or better.
> 
> -- Bruce

-- 
Marco Antoniotti ========================================================
NYU Courant Bioinformatics Group        tel. +1 - 212 - 998 3488
719 Broadway 12th Floor                 fax  +1 - 212 - 995 4122
New York, NY 10003, USA                 http://bioinformatics.cat.nyu.edu
                    "Hello New York! We'll do what we can!"
                           Bill Murray in `Ghostbusters'.
From: Bruce Hoult
Subject: Re: *ML style Union Types [Re: On nil qua false]
Date: 
Message-ID: <bruce-FF2E76.13370701122001@news.paradise.net.nz>
In article <··················@octagon.mrl.nyu.edu>, Marco Antoniotti 
<·······@cs.nyu.edu> wrote:

> Bruce Hoult <·····@hoult.org> writes:
> 
> > In article <··············@teonanacatl.andreas.org>, Andreas Bogk 
> > <·······@andreas.org> wrote:
> > 
> > > Before this discussion, I was also unaware of the fact that separating
> > > false and the empty list in Dylan wouldn't work so smoothly if it
> > > hadn't been for type unions and the default keyword in the ELEMENT
> > > function.
> > 
> > I think type unions are an *extremely* important language feature, and 
> > one I miss greatly in C++ & Java.  They allow you to do OO kinda stuff 
> > without requiring things to have a common base class.  In fact, if I 
> > understand it properly, the ML languages effectively use type-union 
> > *instead* of inheritance.  In ML you pick them apart with pattern 
> > matching, but I think instead combining them with Generic Functions is 
> > just as good, or better.
>
> I think this is an interesting concept, and I know that it is one of
> the things the *ML crowd uses a lot (IMHO almost as an alternative to
> macro processing).
> 
> Any idea about how to render them in CL (if possible)?

The first thing to understand is that type-union is a property of 
*bindings*, rather than of *objects*.  So it is not at all the same 
thing as, say, C union types, or Pascal variant records.  Any particular 
obeject has a concrete type, not a union type, but objects of different 
types may be bound to the same variable at different times.

So normal bindings in Lisp are in fact type-union(everything you can 
think of).  The coolness comes in when you start declaring the types of 
variables, because it allows you to say not just the a variable is of a 
particular type, but that a variable might be of type "foo" or "bar" or 
"baz" but it can't be anything else.  This enables mechanical checks 
that you covered all the cases (and makes manual checks easier), and 
enables compiler optimizations.

This just doesn't exist in C or Pascal.  At least not without a lot of 
unsafe typecasting.  Any Object-Oriented language of course provides 
this idea, but in a quite limited way: the different types must all have 
a common base class.

Type-union, on the other hand, lets you do it with *any* types.  This is 
used to good effect in *ML, where the standard type declaration not only 
makes a union type, but also defines the individual types -- effectively 
record or tuple types -- that make it up.

Type-union does something useful with data.  Generic Functions do the 
same useful thing with computations.  You don't have to decide in 
advance which virtual functions go with which classes.  You can always 
add entirely new GFs at any time, and specialize methods in them on any 
type you want -- even someone else's class, or something from the 
standard library.


The two together provide a powerful form of OO that doesn't depend on 
inheritance at all.

-- Bruce
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwlmgp2cgq.fsf@shell01.TheWorld.com>
Andreas Bogk <·······@andreas.org> writes:

> > But in answer to your question, no, the (FALSE-OR type) thing moves
> > in the wrong direction.  It IS a useful technology for places where it
> > was not possible to find a degenerate element within the set.
> 
> Can I understand this answer as saying that making natural nulls false
> and using false-or are two techniques addressing the same issue, where
> the former applies to less cases, but is better suited to them?

("fewer" cases).  Yes, probably.  [I'm not positive that's the statistic,
but propbably it is and it's not worth fussing about.  The essence of
your remark sounds right.]
 
> The two approaches seem mutually exclusive to me, though.  Once your
> type has an instance that is false, (FALSE-OR type) becomes useless in
> that it doesn't behave like a naive user would expect.

I don't think that's always got to be true.  It might just expose that
FALSE-OR was the wrong name for that type-operation in a Lisp that
subscribed to the other theory.  You'd probably call it NIL-OR or
something like that, to empahsize which FALSE you were using.  If you
didn't just use or(singleton(#f),othertype).
 
> > For example, had () and NIL and #f been all separate to start, I could
> > imagine arguing to make () false, just as I have noted that I'd be
> > happy if "" was false and #() was false.  However, I can't imagine
> 
> If I understand it correctly, people argue that the equality of NIL
> and the empty list is elegant, because any function returning false
> for whatever reason still returns a valid list.  Wouldn't introducing
> multiple falses bear the risk of getting a false of the wrong type
> where you don't expect it?  For the records, while I haven't written
> anything bigger than ten lines in MOO, I never experienced a problem
> of that nature.

You just have to know which kind of false you're supposed to return
(if the client is dictating terms) or which type of false someone
says they are returning (if the user is).  Today I had to write
 room.tell_contents($set_utils:set_difference(others,seen||{}));
to paper over just this problem.  It's rare that this is needed,
but it does happen. It's also very easy to work around, and a reasonable
price to pay for the cases where it works.  As with all things, any
well-defined spec does not leave any confusion on this point.
It's easy to think you'd be confused if you think that the return
value is left to chance.  (And, frankly, some moos are very anarchic
with no one spec'ing anything.  But I can assure you that this kind of
problem is the LEAST of the troubles that results from anarchy. :-)

> /When/ introducing multiple falses, I'd argue for introducing a
> canonical false as well.

Then you could again call false-or by the name you wanted. :-)
Again, this is why I say context matters so much when doing language
design.
 
However, I don't see the value of a canonical false.  It would only 
make people feel bad about using some equally legit value.  The truth
has to be that the canonicality, such as it is, is context-dependent,
and more precisely, spec-dependent.  You could, of course, make
something like (BOOLEAN-UTILS:CANONICAL-FALSE 0) => NIL, but then
that doesn't keep you from having (NUMBER-UTILS:CANONICAL-FALSE NIL) => 0.
As they say, "the nice thing about standards is that there are so 
many of them". (Ok, so it's kind of out of context, but it seemed to
sort of apply...)

> > Internationalization terms, if nothing else.  And certainly if I were
> > telling you to merge a faluse value with some random number seed, I
> > wouldn't try to figure out what a degenerate seed was so that I could
> > argue it should be false.  I'd just say (FALSE-OR RANDOM-STATE).
> 
> I think we can safely say that we agree on this one.
> 
> > But there are places where there are natural nulls, and lists and
> > arrays (including, of course, strings) are among them.  I don't feel a
> 
> From your example below, I conclude this should also be true for
> integers.

Well, your language has to speak to what values are true and what are false
and whether any are in between.  There's a second question of canonical
truth.  Lisp speaks to both.  But i"m not sure how this matters.
 
> > need for an extra type in a great many situations.  This is evident in
> > the number of applications that do (PUSH X (GETHASH A B)) where they
> > don't check to see if (GETHASH A B) returns NIL, NIL or NIL, T because
> > it doesn't matter to them. 
> 
> The price to pay for not having it would be having to write: 
> 
>   (PUSH X (GETHASH A B :DEFAULT NIL))
> 
> although one could argue that this makes the intent "I know what to do
> when I don't find the element" better visible to the reader.

You could.  Then again, even defaults should have default values.
There are reasons not all args are required.  Don't confuse "what would
suffice" with "what someone might want to say".  Plainly the default
arg to gethash (which is optional, not keyword, btw) is more powerful.
I probably should have used a diffeernt function that didn't have this arg.

> > Also, in languages where you have more than one false, you can choose
> > to do (EQ value 'particular-false-value) and to treat the other values
> > differently.
> 
> That's true.  It's probably the same overhead as having to write
> (NULL? value) in languages where the null values aren't false.

Well, I was also thinking of cases where I sometimes have switch
values that are VERBOSE = NIL, T, or :ALWAYS, where I do
 (EQ VERBOSE 'T)
in some cases and just
 VERBOSE
in others.
 
> This probably reduces the question of which is "better" to the
> question of "what case arises more often", and this is so dependent on
> style and personal preferences that no answer can be given.
> 
> > list might be NIL, and a probelm might result.  SO I say back, suppose
> > a FOO is represented as a boolean.  (That would mean I only ever have 
> 
> Yes, in case FOO can be a boolean all is lost, and you have to find
> another trick.  In Dylan code, one often finds idioms like this:
> 
> define constant $not-supplied = pair(#f, #f);
> 
> define method foo(bar, #key baz = $not-supplied)
>  ...
> end;
> 
> Unsupplied keyword arguments default to #f.  The purpose of this idiom
> is to differentiate between an unsupplied argument, and #f being
> supplied to the function.  When not supplying and supplying #f are
> semantically the same, the trick is not needed.

As long as you don't call the function recursively, or as long as you
don't call some other function that uses the same constant.

The right way to handle this is with supplied-p args of CL.
If you think supplied-p is a good concept, which I'm somewhat mixed on.
I use it.  But I always hate it when I do because compositional
algebra for "pass-through functions" is painful.

> $not-supplied is some random object on the heap that's only equal to
> itself, and not exported from the module.  So there's no way that
> outside code can call this function and pass $not-supplied.
> 
> > And even as to degree, moving it in the direction of separation means
> > more typing for people, and some people seem to regard that as "good"
> > while others don't, so even the directionality is up for grabs.
> 
> Requiring more typing is not a a good thing per se.  Separating
> semantically what is separate conceptually is a good thing.  

No, that's a value judgment.  It's only a bad thing when a confusion will
certainly result.  In most cases, it's in a gray area between those two.
This entire discussion is made up of words taht are blurry.  Separating
our individual thoughts into things that have no type overlap would make
it huger than either of us would want to imagine.  And the result would
not be necessarily any better since then none of us would read the other's
words at all.

> Making
> life easy for a programmer is a good thing too.  The two often move in
> different directions, and the right balance is certainly a matter of
> personal taste.

Making life easy for the programmer is, imo, the only goal here.
The only place where making a programmer write more words is better
is when it makes his life easier in the long run.
From: Kaz Kylheku
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <jA9N7.793$nm3.99698@news1.rdc1.bc.home.com>
In article <··············@teonanacatl.andreas.org>, Andreas Bogk wrote:
>···@ashi.footprints.net (Kaz Kylheku) writes:
>
>> In places where the Scheme language report says that the result of an
>> expression is unspecified, or that an evaluation order is unspecified,
>> what design rule is being followed?
>
>"Leave some freedom to the poor implementors."
>
>I'll refrain from judging this.

But not from judging the role of NIL in Lisp.
From: Alain Picard
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <861yijw8hi.fsf@gondolin.local.net>
Andreas Bogk <·······@andreas.org> writes:

> 
> As a feature, it feels like a convenience hack so you can write 
> (if foo) instead of (unless (empty? foo)).
> 
> That's not much of a gain, given that you have just violated the
> design rule of having a way to differentiate between a valid and an
> invalid result.

Please, pay attention.  

People have already explained that

  1) There is already a large community who think it's a feature, not 
     what you condescendingly call a "design rule violation"

  2) A lot of these people are very smart

  3) They've already given you examples of the idioms which are natural
     in CL to "differentiate between valid and invalid results".

So what remains?  It still looks like, to me, that it's a different way
of doing things than you're used to, so you immediately conclude it's bad.

One thing you'll learn, if you persevere with CL, is that some of the
brightest minds ever to touch a keyboard have contributed to its design,
directly or indirectly (i.e. via historical accidents).

I've learned that, when I read CLtL2, if I don't understand something,
or think I disagree with something, I need to look harder, because it
is almost certainly _I_ who is missing something.

I suggest you adopt that attitude for a couple of years, write lots of
code, and _THEN_ come tell this newsgroup why nil == () is bad in 
real day-to-day CL usage, AND what you propose is better.

Who knows?  You just _might_ be a genius, come up with a great innovation,
and get the language changed.


-- 
It would be difficult to construe        Larry Wall, in  article
this as a feature.			 <·····················@netlabs.com>
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-79ABC1.22365028112001@news.paradise.net.nz>
In article <··············@gondolin.local.net>, Alain Picard 
<·······@optushome.com.au> wrote:

> So what remains?  It still looks like, to me, that it's a different way
> of doing things than you're used to, so you immediately conclude it's bad.
> 
> One thing you'll learn, if you persevere with CL, is that some of the
> brightest minds ever to touch a keyboard have contributed to its design,
> directly or indirectly (i.e. via historical accidents).

What *you* have missed, is that some of those exact same brightest minds 
to ever touch a keyboard went from Common Lisp to design a new language 
and did a few things differently the second time around.

Are you saying that you're brighter than Moon?

-- Bruce
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfw7ksb6to1.fsf@shell01.TheWorld.com>
Bruce Hoult <·····@hoult.org> writes:

> In article <··············@gondolin.local.net>, Alain Picard 
> <·······@optushome.com.au> wrote:
> 
> > So what remains?  It still looks like, to me, that it's a different way
> > of doing things than you're used to, so you immediately conclude it's bad.
> > 
> > One thing you'll learn, if you persevere with CL, is that some of the
> > brightest minds ever to touch a keyboard have contributed to its design,
> > directly or indirectly (i.e. via historical accidents).
> 
> What *you* have missed, is that some of those exact same brightest minds 
> to ever touch a keyboard went from Common Lisp to design a new language 
> and did a few things differently the second time around.

It's not obvious how anything Alain has said neglects this.

Also, Steele, for example, designed Scheme first and then CL.  Was CL a
rejection of Scheme for him?  Was his later work with C++ a rejection of CL?
Was his later work with Java a rejection of C++?  I suspect some of the
answers here are "yes" and some "no", but I wouldn't know without asking him.
I point it out to say that the single-bit of information represented in
the yes/no answer to the question "used to work with X now works for Y?"
is not the same as the single-bit of information represented in the statement
"has rejected all aspects of X for Y".  I quote (or is it paraphrase, since
I'm not sure I have an exact wording that I think is best) 
Pitman's Two-Bit Rule: when representing two bits of information, 
use two bits to do it.

Further, as I have pointed out many times before, there is no "good/bad"
distinction in the abstract.  Good and bad are dictated by context.  When
you make a new language, you make a new ecology.  What is good and bad 
in that new ecology is what makes sense there in context.

That's the reason that the apparent kludge of ()/#f being the same works in
CL.  Tons of other decisions are of similar kind.  NIL's are padded out for
return values where not supplied.  NIL can be car/cdr'd.  We use type
"designators" all over where other languages would use raw types only.
There is a certain design consistency here that is underappreciated, and that
I hoped to highlight in the spec when I invented the designator concept
where previously there had been only "a lot of special cases".  Just because
people are bad at articulating it doesn't mean they are stupid.  

And saying
 (when foo ...)
is not the same as saying
 (when (not (null foo)) ...)
at the intention level.  It carries a subtlely different connotation for
some of us.  The former, to me, asks "if there is a foo" and the latter asks
"if there foo is not empty".  These are represented the same in CL, but I
prefer the expressional sense of the former.  In my mind, when a list goes to
empty, I like to think of it as not existing.  I don't think of it as existing
but empty.  It works out programmatically nicely to have the two be the same.
It's fine for people to think otherwise, but it's not fine for them to pretend
that the language doesn't intend to support my way of thinking.

If you really want a language with no ability to pun on types, I
really do suggest Scheme.  Not just because it makes this decision
differently (or "right", if you prefer to say that) but because its
community will reinforce in you the notion that this is the only
possible legitimate point of view, and give you a generally warm sense
of fuzzy that you have come home.  Its leaders will also make it a
priority to ruthlessly seek out lurking places where anyone is punning
for convenience and to callously shun such people, and that will
probably make you feel good about your leaders and the community they
have created.  And that's WHY we have separate political parties, er,
languages.  Because people want different things.  In this political party,
we tolerate diverse points of view.  You can write (not (null x))
and I can write x.  We both know what each other means.  And our code
interacts.  If you don't like that, and prefer to interact with people
who agree with you that only one point of view is possible, then this is
not the language for you.  It will not just frustrate you on this point.
It will frustrate you on a whole host of issues where the design style
has been of similar character.

> Are you saying that you're brighter than Moon?

I'll save Alain from having to point out that this kind of remark is
not a useful debate tactic.  Also, you imply by this that Moon thinks
nil/false thing was done wrong in CL.  I personally doubt you'll get him
to make such a claim, but in any case it's unfair of either your or me
to associate him with a position without asking him to state it for himself.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-F1C168.00540529112001@news.paradise.net.nz>
In article <···············@shell01.TheWorld.com>, Kent M Pitman 
<······@world.std.com> wrote:

> Bruce Hoult <·····@hoult.org> writes:
> 
> > In article <··············@gondolin.local.net>, Alain Picard 
> > <·······@optushome.com.au> wrote:
> > 
> > > So what remains?  It still looks like, to me, that it's a different 
> > > way
> > > of doing things than you're used to, so you immediately conclude it's 
> > > bad.
> > > 
> > > One thing you'll learn, if you persevere with CL, is that some of the
> > > brightest minds ever to touch a keyboard have contributed to its 
> > > design,
> > > directly or indirectly (i.e. via historical accidents).
> > 
> > What *you* have missed, is that some of those exact same brightest 
> > minds 
> > to ever touch a keyboard went from Common Lisp to design a new language 
> > and did a few things differently the second time around.
> 
> It's not obvious how anything Alain has said neglects this.
> 
> Also, Steele, for example, designed Scheme first and then CL.  Was CL a
> rejection of Scheme for him?  Was his later work with C++ a rejection of 
> CL?  Was his later work with Java a rejection of C++?

Of course you'd hav to ask him to find out, but I suspect that he's been 
seeking a wider audience for his ideas, as first developed in the 
various "lambda the ultimate ..." papers and no doubt refined since.


> Just because people are bad at articulating it doesn't mean they
> are stupid.  

That applies in both directions, though you wouldn't know it to read 
many of the replies to myself and Andreas here.


> And saying
>  (when foo ...)
> is not the same as saying
>  (when (not (null foo)) ...)
> at the intention level.  It carries a subtlely different connotation for
> some of us.

And Andreas and I have much the same subtly different connotation.  The 
only real difference is that we think that perpetuating the old "the 
list is the fundamental datastructure in Lisps" myth is doing the Lisp 
community (of which we are a part) a disservice.

We want to be able to use the *same* subtle connotation for data types 
other than lists without somehow bringing in an implicit assumption that 
a list is a valid value where you want to convey the idea that something 
is either a string or doesn't exist, or is either a number or doesn't 
exist, or is either a hash table or doesn't exist.


> If you really want a language with no ability to pun on types, I
> really do suggest Scheme.

Scheme is way too limiting.  We've got far more in common with CL than 
we have with Scheme.  Scheme isn't even an option any more than Jensen & 
Wirth Pascal is an option.


> If you don't like that, and prefer to interact with people
> who agree with you that only one point of view is possible, then this is
> not the language for you.  It will not just frustrate you on this point.
> It will frustrate you on a whole host of issues where the design style
> has been of similar character.

False premise, false conclusions.


> > Are you saying that you're brighter than Moon?
> 
> I'll save Alain from having to point out that this kind of remark is
> not a useful debate tactic.

Funnily enough I know this.  The point of my making this remark is that 
this is *exactly* the tactic that has been used against myself for some 
time, and is now being used against Andreas in, for example, Alain's 
message.

It is an invalid debating tactic and I totally reject implications based 
upon it.

Whether particular things are good or bad should be decided on the basis 
of logic, not on the basis of argument from authority.  Of course that 
becomes difficult when you explicitly reject logic, as Erik just did.  I 
don't know what that leaves, other than tradition and accident.

-- Bruce
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfw7ksbozdl.fsf@shell01.TheWorld.com>
Bruce Hoult <·····@hoult.org> writes:

> > If you really want a language with no ability to pun on types, I
> > really do suggest Scheme.
> 
> Scheme is way too limiting.  We've got far more in common with CL than 
> we have with Scheme.  Scheme isn't even an option any more than Jensen & 
> Wirth Pascal is an option.

I think this is not coincidence.  I think the cause of Scheme being
what you perceive as limiting and cause of Scheme making what you see
as the "right" choice on this issue are the forces of the same or similar
kind.  That is, you have a certain style of design and it leads to some
consequences you like and some you don't like.

> > If you don't like that, and prefer to interact with people
> > who agree with you that only one point of view is possible, then this is
> > not the language for you.  It will not just frustrate you on this point.
> > It will frustrate you on a whole host of issues where the design style
> > has been of similar character.
> 
> False premise, false conclusions.

I wasn't really meaning to make the statement for the purpose of
advancing its logic.  It was making it to be honest-to-goodness
helpful.  I didn't want to say "If you don't like it, go elsewhere"
because this would sound like I was just trying to shun you, which
would not be a fair assessment.  I'm just saying that languages are
political parties and people should associate with one that supports
their view.  Moreover, as to this political party, its core membership
(that is, as embodied in J13) apparently agrees that the cost of
opening the existing standard for tinkering is prohibitively high.  It
is not up for debate.  I have to say "apparently agrees" and can't say
"agrees" since I'm not its spokesperson (no one is), but its actions
in having declined the chance to open itself for change do, I think,
more or less speak for themselves.  You're welcome to disagree with
whatever you like, and to stick around fuming over this, but the issue
is really not up for debate in any practical sense.  And I believe you
are just spinning your wheels and wasting valuable time (mine, yours,
and other people's) over something that isn't important enough.

Look, life is short.  We're all getting older.  The move to CL was
about putting Maclisp to bed and saying "it's time to argue over a new
set of things".  This discussion is very "maclisp" and is just done.
I don't expect to look back when I'm on my deathbed and say "I wish
I'd spent more time looking into Bruce's assertion I was wrong on
this".  And I don't want either of our tombstones to read "they almost
reached agreement about the empty-list/false thing".  I'm much more likely
to say "damn, I wish I could have back all those minutes I wasted
in that stupid, pointless discussion".  This has been talked to death.
There are no more points to be made.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-DDFADF.13590629112001@news.paradise.net.nz>
In article <···············@shell01.TheWorld.com>, Kent M Pitman 
<······@world.std.com> wrote:

> Moreover, as to this political party, its core membership
> (that is, as embodied in J13) apparently agrees that the cost of
> opening the existing standard for tinkering is prohibitively high.  It
> is not up for debate.

Once again we have this defensiveness, based on a false premise.

I don't want to change CL.  I certainly don't have the power to change 
CL, even if I wanted to.  It is, as you say, "done".  Fine.  Can we 
please move on from this false premise?

What I want to do is to *understand* CL, just for my own pure 
intellectual curiosity.  I want to know not only what *is* in CL, but 
*why* it is.  If there's a logical reason then I'd like to know it.  If 
there are special advantages conferred by something that make certain 
things easier to do then I want to learn about that too.  And if 
something is just historical accident and it hasn't been judged worth 
the pain of changing then that answers my question too.

Far from wanting to change CL, what I want to do is to see if there is 
anything that should be changed in Dylan.  And *that* I believe I have a 
strong chance of doing.  I can implement new things in CMU Gwydion 
Dylan, try them out, and if they work well there is an excellent chance 
of them being propogated to the other implementations.

-- Bruce
From: Tim Bradshaw
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <fbc0f5d1.0111290328.662f01a2@posting.google.com>
Bruce Hoult <·····@hoult.org> wrote in message news:<···························@news.paradise.net.nz>...
> 
> What I want to do is to *understand* CL, just for my own pure 
> intellectual curiosity.  I want to know not only what *is* in CL, but 
> *why* it is.  If there's a logical reason then I'd like to know it.  If 
> there are special advantages conferred by something that make certain 
> things easier to do then I want to learn about that too.  And if 
> something is just historical accident and it hasn't been judged worth 
> the pain of changing then that answers my question too.

Well, here's how you understand CL: write large programs in it.  No
amount of discussion of the language is a substitute for this, because
CL is a language which is *about* being able to write large programs,
if it's about anything.  Until you've written thousands of lines of
code you just won't understand why it is the way it is (and I don't
mean NIL/false here, I mean the language).  I've been writing CL for
13 years or something, and I *still* have moments of insight into
things.  There simply is no substitute for experience.

--tim
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215995617168581@naggum.net>
* Bruce Hoult
| What I want to do is to *understand* CL, just for my own pure
| intellectual curiosity.  I want to know not only what *is* in CL, but
| *why* it is.

  But you seem to reject the answers you get!  You keep asking even when
  you get the perfectly honest and full answer.  That is the insanity.
  Despite what you say, you do not appear to be satisfied with the truth.
  In other words, you communicate that you think people are guilty of
  hiding something from you, and that is actually _very_ offensive.

| If there's a logical reason then I'd like to know it.

  You, too, seem to think that you can have logic without premises, or at
  least different premises from what _you_ have.  Why is that?

| Far from wanting to change CL, what I want to do is to see if there is 
| anything that should be changed in Dylan.

  Then why are you not discussing this in comp.lang.dylan?  And why are you
  talking about how Dylan does things all the time if you want to change
  Dylan?  Sorry, this does not compute.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-6573BB.19210229112001@news.paradise.net.nz>
In article <················@naggum.net>, Erik Naggum <····@naggum.net> 
wrote:

> * Bruce Hoult
> | What I want to do is to *understand* CL, just for my own pure
> | intellectual curiosity.  I want to know not only what *is* in CL, but
> | *why* it is.
> 
>   But you seem to reject the answers you get!  You keep asking even when
>   you get the perfectly honest and full answer.  That is the insanity.

On the contrary, I really appreciate the thoughtful answers I get from 
Kent Pitman, Pierre Mai and others who while I sometimes fail to 
communicate what I mean clearly enough always remain polite.


> | Far from wanting to change CL, what I want to do is to see if there is 
> | anything that should be changed in Dylan.
> 
>   Then why are you not discussing this in comp.lang.dylan?

Because I am in the process of learning CL and this seems to be where 
the CL people are.


>   And why are you talking about how Dylan does things all the time
>   if you want to change Dylan?  Sorry, this does not compute.

Because it is easier to read unfamilar code than to write it.  If I 
express some point in Dylan then I can do that quickly an precisely 
without errors and probably everyone can understand it, wheras if I try 
to put it into CL -- especially if it's a corner of the language I'm in 
the process of learning about -- then I'm likely to make mistakes which 
obscure the point.

-- Bruce
From: Wade Humeniuk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <9u5joh$jl7$1@news3.cadvision.com>
> >   And why are you talking about how Dylan does things all the time
> >   if you want to change Dylan?  Sorry, this does not compute.
>
> Because it is easier to read unfamilar code than to write it.  If I
> express some point in Dylan then I can do that quickly an precisely
> without errors and probably everyone can understand it, wheras if I try
> to put it into CL -- especially if it's a corner of the language I'm in
> the process of learning about -- then I'm likely to make mistakes which
> obscure the point.

If you need some help learning CL maybe you could post a substative (a
non-trivial real program) amount of code in Dylan and people could write the
equivalent solution in CL.  Then both sides could learn something.

Wade
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-164061.10145430112001@news.paradise.net.nz>
In article <············@news3.cadvision.com>, "Wade Humeniuk" 
<········@cadvision.com> wrote:

> If you need some help learning CL maybe you could post a substative
> (a non-trivial real program) amount of code in Dylan and people could
> write the equivalent solution in CL.  Then both sides could learn
> something.

That certainly might be interesting, but I wouldn't dream of asking 
anyone here to do that much work.

Also, although I do have a couple of reasonably substantive Dylan 
programs in the public domain (e.g. an ICFP2000 contest ray tracer and 
an ICFP2001 contest markup language optimizer, both available from cvs 
at www.gwydiondylan.org) the translation of the vast majority of that 
code to CL is a simple syntactic transformation which won't teach anyone 
anything.  It's the dusty little corners of the language which are more 
interesting, and the more likely to surprise.

-- Bruce
From: Wade Humeniuk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <9u6aq8$r5g$1@news3.cadvision.com>
> > If you need some help learning CL maybe you could post a substative
> > (a non-trivial real program) amount of code in Dylan and people could
> > write the equivalent solution in CL.  Then both sides could learn
> > something.
>
> That certainly might be interesting, but I wouldn't dream of asking
> anyone here to do that much work.
>
> Also, although I do have a couple of reasonably substantive Dylan
> programs in the public domain (e.g. an ICFP2000 contest ray tracer and
> an ICFP2001 contest markup language optimizer, both available from cvs
> at www.gwydiondylan.org) the translation of the vast majority of that
> code to CL is a simple syntactic transformation which won't teach anyone
> anything.  It's the dusty little corners of the language which are more
> interesting, and the more likely to surprise.

I looked at some of your ICFP2001 code.  Your are right (though I do not
know dylan well) that it seems to be a simple syntatic translation.  The
lesson for me in this is that CL has all of the functionality of Dylan and
is very similar.  My questions back are:

Did any of those dusty litle corners make any difference in your program?
The answer probably is that you did not use any of the little dusty little
corners.

Would you say when Dylan was created that its model was CL and those dusty
little corners from CL  where not included in Dylan?

Are you asking if some of those dusty corners left behind would be useful to
be included into Dylan?

Is this what you are trying to determine.  That would be a more interesting
question.

Perhaps you can make a list of issues (differences, not the nil/()/false
issue) you consider useful looking into?  Maybe then you can get some input
if they would be good to put into Dylan.

Wade
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-BF89B1.13545530112001@news.paradise.net.nz>
In article <············@news3.cadvision.com>, "Wade Humeniuk" 
<········@cadvision.com> wrote:

> I looked at some of your ICFP2001 code.  Your are right (though I do not
> know dylan well) that it seems to be a simple syntatic translation.  The
> lesson for me in this is that CL has all of the functionality of Dylan 
> and is very similar.

Very similar: yes.  *All* the functionality: no, that isn't true, in 
either direction.


Dylan is CLOS-all-the-way-down, more like Smalltalk than CL.  Dylan 
allows the user to trade-off dynamism at runtime for (hopefully) better 
optimization and speed, but even at its most dynamic is less flexible at 
runtime than CL.  There is no eval so you can't do a REP loop.  Dylan is 
intended to be a compiled language in which compile time is clearly 
separated from runtime, both so the compiler can make more assumptions 
about the code and optimize harder, but also so that programs *don't* 
expect to have the compiler there at runtime so they can run on smalle 
machines and/or have smaller image sizes.  That's becoming less and less 
important every year, of course, but full CL is still hard to fit onto a 
PDA.  Then there are the syntactic differences.  I can and do program 
happily in C, Perl, Dylan, Scheme, PostScript, OCaml so I can cope 
easily with any number of different syntax styles, but I find that I 
*do* prefer what Lisp calls "special forms" to be written using either 
keywords or punctuation different from that used for expressions.  Not 
that the actual syntax choosen by the designers of Dylan thrills me all 
that much.  But I can certainly live with it, and for me it's better 
than S-expressions.


> My questions back are:
> 
> Did any of those dusty litle corners make any difference in your program?
> The answer probably is that you did not use any of the little dusty 
> little corners.

That's going to depend on the exact definition of "dusty little 
corners".  There is certainly some use of that sort of thing in, for 
example, the way I hid some very low level efficient bit banging behind 
a high level interface.


> Would you say when Dylan was created that its model was CL and those 
> dusty little corners from CL  where not included in Dylan?

CL was certainly a major influence (as was Smalltalk and C++ (or Simula, 
if you prefer)), and I understand that trying to improve on some of the 
decisions and historical accidents in CL was a definite goal.


> Are you asking if some of those dusty corners left behind would be useful 
> to be included into Dylan?

Yes.  New ideas aren't always better than old ones and improvements 
aren't always.  Only experience can tell you that.  After using it for a 
few years I know a number of things that I think could be done better in 
Dylan.  I don't know whether or not CL does those things any better, 
because I don't yet know CL that well.  But I suspect that it *is* the 
dusty corners that I don't know well, rather than the normal stuff.  I 
mean, if someone asks "how can I prevent my class from being 
instantiated", I can say to myself "well maybe you could use the C++ 
technique of declaring a virtual function and put '= 0' on the end 
instead of implementing it, or else maybe you could use the Dylan 
technique of adding a method to the make() or initialize() GFs that 
throws an error".  On any given question, the chances are 99% that the 
Dylan technique is also applicable to CL, and I just need to find the 
correct name for it e.g. make-instance instead of make.

Now this probably *would* be a dusty corner of CL to a C++ programmer, 
but it's obvious to a Dylan programmer.


> Is this what you are trying to determine.  That would be a more 
> interesting question.
> 
> Perhaps you can make a list of issues (differences, not the
> nil/()/false issue) you consider useful looking into?  Maybe then
> you can get some input if they would be good to put into Dylan.

I've been working on assembling such a list for some time.

-- Bruce
From: Nils Goesche
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <lkr8qhn6e1.fsf@pc022.bln.elmeg.de>
Bruce Hoult <·····@hoult.org> writes:

> In article <················@naggum.net>, Erik Naggum <····@naggum.net> 
> wrote:
> 
> > * Bruce Hoult
> > | What I want to do is to *understand* CL, just for my own pure
> > | intellectual curiosity.  I want to know not only what *is* in CL, but
> > | *why* it is.
> > 
> >   But you seem to reject the answers you get!  You keep asking even when
> >   you get the perfectly honest and full answer.  That is the insanity.
> 
> On the contrary, I really appreciate the thoughtful answers I get from 
> Kent Pitman, Pierre Mai and others who while I sometimes fail to 
> communicate what I mean clearly enough always remain polite.

Actually, Erik's first postings on the subject, the ones where he
clearly explained the issue several times, were perfectly polite,
too; see for instance

http://groups.google.com/groups?q=naggum+false+nil+qua&hl=en&rnum=1&selm=3215382911849059%40naggum.net

But for some strange reason, none of those postings of his were
answered by the ``other side''.  That's why I, too, got the impression
that you people weren't actually interested in learning about the
issue but rather in teaching everyone how necessary it is to introduce
an additional value for boolean `false', like Dylan or Scheme, without
giving a single reason why that would be better, BTW.

Regards,
-- 
Nils Goesche
"Don't ask for whom the <CTRL-G> tolls."

PGP key ID 0x42B32FC9
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-5A5398.11051930112001@news.paradise.net.nz>
In article <··············@pc022.bln.elmeg.de>, Nils Goesche 
<······@cartan.de> wrote:

> > On the contrary, I really appreciate the thoughtful answers I get from 
> > Kent Pitman, Pierre Mai and others who while I sometimes fail to 
> > communicate what I mean clearly enough always remain polite.
> 
> Actually, Erik's first postings on the subject, the ones where he
> clearly explained the issue several times, were perfectly polite,
> too; see for instance
> 
> http://groups.google.com/groups?q=naggum+false+nil+qua&hl=en&rnum=1&selm=3
> 215382911849059%40naggum.net
> 
> But for some strange reason, none of those postings of his were
> answered by the ``other side''.  That's why I, too, got the impression
> that you people weren't actually interested in learning about the
> issue but rather in teaching everyone how necessary it is to introduce
> an additional value for boolean `false', like Dylan or Scheme, without
> giving a single reason why that would be better, BTW.

Well, yes, that post is reasonable and calm and in fact I don't disagree 
with anything in it, as far as it goes.  And I don't want to restart 
this whole thread either.

The only issue I have, as I said when I joined the thread half a dozen 
messages later, is how you tell whether a function searching for a list 
and returning it found it and it was empty, or whether it was not found 
at all.

This question doesn't apply to either "member" or "assoc" used as 
examples in Erik's post.  Or, at least, if it does apply the answer is 
something like "the people who designed these functions were aware of 
the problem you mention and side-stepped the problem by returning not 
the value being sought, but a data structure containing the value e.g. 
assoc returns the entire cons containing both the key and the value, not 
just the value".

Is this technique used by everyone else when they write functions that 
return lists in their own CL code?  I don't know.  Certainly no one even 
*mentioned* it or said "yes, it's a problem, but we get around it by 
using this idiom".  They just said "it's not a problem".

-- Bruce
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcvd7219ozg.fsf@blizzard.OCF.Berkeley.EDU>
Bruce Hoult <·····@hoult.org> writes:

> In article <··············@pc022.bln.elmeg.de>, Nils Goesche 
> <······@cartan.de> wrote:
> 
> > > On the contrary, I really appreciate the thoughtful answers I get from 
> > > Kent Pitman, Pierre Mai and others who while I sometimes fail to 
> > > communicate what I mean clearly enough always remain polite.
> > 
> > Actually, Erik's first postings on the subject, the ones where he
> > clearly explained the issue several times, were perfectly polite,
> > too; see for instance
> > 
> > http://groups.google.com/groups?q=naggum+false+nil+qua&hl=en&rnum=1&selm=3
> > 215382911849059%40naggum.net
> > 
> > But for some strange reason, none of those postings of his were
> > answered by the ``other side''.  That's why I, too, got the impression
> > that you people weren't actually interested in learning about the
> > issue but rather in teaching everyone how necessary it is to introduce
> > an additional value for boolean `false', like Dylan or Scheme, without
> > giving a single reason why that would be better, BTW.
> 
> Well, yes, that post is reasonable and calm and in fact I don't disagree 
> with anything in it, as far as it goes.  And I don't want to restart 
> this whole thread either.
> 

> The only issue I have, as I said when I joined the thread half a dozen 
> messages later, is how you tell whether a function searching for a list 
> and returning it found it and it was empty, or whether it was not found 
> at all.

I could have sworn this was answered (in fact, I'm pretty sure I
addressed this myself).  Do like the other functions in CL do (not
assoc) -- return two values, or have :error-p and :default keyword
arguments.

  (my-association-finder (gensym) some-data-structure)
    => NIL;
       NIL
or
  (my-association-finder (gensym) some-data-structure)
  Error in function MY-ASSOCIATION-FINDER: Item not found ...
or
  (my-association-finder (gensym) some-data-structure
                         :error-p nil :default :not-found)
    => :NOT-FOUND

> This question doesn't apply to either "member" or "assoc" used as 
> examples in Erik's post.  Or, at least, if it does apply the answer is 
> something like "the people who designed these functions were aware of 
> the problem you mention and side-stepped the problem by returning not 
> the value being sought, but a data structure containing the value e.g. 
> assoc returns the entire cons containing both the key and the value, not 
> just the value".

I don't think this is side-stepping the problem.  If getting the cons
cell were only useful for determining whether or not the item was
found, then I'd agree, but it can be useful to have the cons cell for
other reasons (such as changing the value associated, and having this
change propogate to anything currently holding onto that cons cell).

> Is this technique used by everyone else when they write functions that 
> return lists in their own CL code?  I don't know.  Certainly no one even 
> *mentioned* it or said "yes, it's a problem, but we get around it by 
> using this idiom".  They just said "it's not a problem".

It's not a problem because we have multiple-values and keyword arguments.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-C6E6DB.13075630112001@news.paradise.net.nz>
In article <···············@blizzard.OCF.Berkeley.EDU>, 
···@blizzard.OCF.Berkeley.EDU (Thomas F. Burdick) wrote:

> Bruce Hoult <·····@hoult.org> writes:
> 
> > In article <··············@pc022.bln.elmeg.de>, Nils Goesche 
> > <······@cartan.de> wrote:
> > 
> > > > On the contrary, I really appreciate the thoughtful answers I get 
> > > > from 
> > > > Kent Pitman, Pierre Mai and others who while I sometimes fail to 
> > > > communicate what I mean clearly enough always remain polite.
> > > 
> > > Actually, Erik's first postings on the subject, the ones where he
> > > clearly explained the issue several times, were perfectly polite,
> > > too; see for instance
> > > 
> > > http://groups.google.com/groups?q=naggum+false+nil+qua&hl=en&rnum=1&se
> > > lm=3
> > > 215382911849059%40naggum.net
> > > 
> > > But for some strange reason, none of those postings of his were
> > > answered by the ``other side''.  That's why I, too, got the 
> > > impression
> > > that you people weren't actually interested in learning about the
> > > issue but rather in teaching everyone how necessary it is to 
> > > introduce
> > > an additional value for boolean `false', like Dylan or Scheme, 
> > > without
> > > giving a single reason why that would be better, BTW.
> > 
> > Well, yes, that post is reasonable and calm and in fact I don't 
> > disagree 
> > with anything in it, as far as it goes.  And I don't want to restart 
> > this whole thread either.
> > 
> 
> > The only issue I have, as I said when I joined the thread half a dozen 
> > messages later, is how you tell whether a function searching for a list 
> > and returning it found it and it was empty, or whether it was not found 
> > at all.
> 
> I could have sworn this was answered (in fact, I'm pretty sure I
> addressed this myself).

Yes it was, but we now appear to be into meta-discussion mode.

It's done as far as I'm concerned, and has been for a long time.

-- Bruce
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcv7ks9gd95.fsf@conquest.OCF.Berkeley.EDU>
Bruce Hoult <·····@hoult.org> writes:

> In article <···············@blizzard.OCF.Berkeley.EDU>, 
> ···@blizzard.OCF.Berkeley.EDU (Thomas F. Burdick) wrote:
>
> > I could have sworn this was answered (in fact, I'm pretty sure I
> > addressed this myself).
> 
> Yes it was, but we now appear to be into meta-discussion mode.
> 
> It's done as far as I'm concerned, and has been for a long time.

What the hell are you talking about?  If you *knew* it had been
answered (I figured you'd missed it somehow), why on earth did you
post this?

    Is this technique used by everyone else when they write functions
    that return lists in their own CL code?  I don't know.  Certainly
    no one even *mentioned* it or said "yes, it's a problem, but we
    get around it by using this idiom".  They just said "it's not a
    problem".

Just to be a troll?  Because I can't think of any other reason.  I try
to give people the benefit of the doubt, but shit like this makes it
difficult.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-773774.16331830112001@news.paradise.net.nz>
In article <···············@conquest.OCF.Berkeley.EDU>, 
···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) wrote:

> Bruce Hoult <·····@hoult.org> writes:
> 
> > In article <···············@blizzard.OCF.Berkeley.EDU>, 
> > ···@blizzard.OCF.Berkeley.EDU (Thomas F. Burdick) wrote:
> >
> > > I could have sworn this was answered (in fact, I'm pretty sure I
> > > addressed this myself).
> > 
> > Yes it was, but we now appear to be into meta-discussion mode.
> > 
> > It's done as far as I'm concerned, and has been for a long time.
> 
> What the hell are you talking about?  If you *knew* it had been
> answered (I figured you'd missed it somehow), why on earth did you
> post this?
> 
>     Is this technique used by everyone else when they write functions
>     that return lists in their own CL code?  I don't know.  Certainly
>     no one even *mentioned* it or said "yes, it's a problem, but we
>     get around it by using this idiom".  They just said "it's not a
>     problem".
> 
> Just to be a troll?  Because I can't think of any other reason.  I try
> to give people the benefit of the doubt, but shit like this makes it
> difficult.

No, that is once again meta-discussion.  And perhaps somewhat 
rhetorical.  But I do thank you for your reply.  So we now have:

a) multiple values, with a second "flag" value

b) keyword and/or optional arguments, allowing the user to specifying a 
default disjoint from the expected data type

c) return a data structure (typically a cons) containing the result, 
rather than returning the result directly.

I confess that c) is new to me.  The other two are familiar.

-- Bruce
From: Tim Moore
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <9u6d1n$6j8$0@216.39.145.192>
In article <···························@news.paradise.net.nz>, "Bruce
Hoult" <·····@hoult.org> wrote:


>
> This question doesn't apply to either "member" or "assoc" used as
> examples in Erik's post.  Or, at least, if it does apply the answer is
> something like "the people who designed these functions were aware of
> the problem you mention and side-stepped the problem by returning not
> the value being sought, but a data structure containing the value e.g.
> assoc returns the entire cons containing both the key and the value, not
> just the value".
> Is this technique used by everyone else when they write functions that
> return lists in their own CL code?  I don't know.  Certainly no one even
> *mentioned* it or said "yes, it's a problem, but we get around it by
> using this idiom".  They just said "it's not a problem".  -- Bruce

There are a few techniques.  The one mentioned above is common.
One can also supply a default argument to the getter which is returned if
nothing is found; see "getf".  Still another way is to return an additional
value  indicating if anything was found.  See "gethash".

Tim
From: Kenny Tilton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3C06C58F.15D4F3EB@nyc.rr.com>
Bruce Hoult wrote:
> The only issue I have, as I said when I joined the thread half a dozen
> messages later, is how you tell whether a function searching for a list
> and returning it found it and it was empty, or whether it was not found
> at all.

This may not be a good example. Not there is not a good one out there.
But in this case we are asking a function to answer two questions with
one value. Never a good idea.

Specifically, by your definition of the issue the function is being
asked to return:

1> Some value associated with the input value, if any

2> Whether any value is associated with the input value

Programmers have played cute tricks like that for centuries, but it is
wrong. Makes code confusing. And it is unnecessary, expecially when you
can return multiple values.

I was just reminded of how CL handles optional arguments, where the
function is curious if its client supplied nil or did not supply the
argument. In our app we have:

(defmethod initialize-instance :before ((self PSClass)
                                        &rest iArgs
                                        &key (logical-unit-of-work nil
luw-specified)
                                        &allow-other-initargs)
   (assert luw-specified)
   ...)

The idea being that it is OK to do I/O outside an LUW, just let us know
that you know what you are doing and have not simply forgotten to supply
the luw control block when actually intending an LUW-managed I/O.

But again, that is two diff questions: what luw if any are we using? and
are you thinking clearly in re luws? So CL offers two diff answers, it
does not try to jam two answers into one.

kenny
clinisys
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-2EE791.13045930112001@news.paradise.net.nz>
In article <·················@nyc.rr.com>, Kenny Tilton 
<·······@nyc.rr.com> wrote:

> Bruce Hoult wrote:
> > The only issue I have, as I said when I joined the thread half a dozen
> > messages later, is how you tell whether a function searching for a list
> > and returning it found it and it was empty, or whether it was not found
> > at all.
> 
> This may not be a good example. Not there is not a good one out there.

I agree, my example was not the best.  I think it was posted around 0400 
local time...

-- Bruce
From: Pierre R. Mai
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <871yihxej7.fsf@orion.bln.pmsf.de>
Bruce Hoult <·····@hoult.org> writes:

> The only issue I have, as I said when I joined the thread half a dozen 
> messages later, is how you tell whether a function searching for a list 
> and returning it found it and it was empty, or whether it was not found 
> at all.

GETHASH is a function that can be employed in situations where an
empty list, and "didn't find anything" are distinct situations.  Its
approach is one, that should make Andreas very happy, in that it uses
true out-of-band signalling to signal the presence or absence of an
entry, via its second return value.[1]

Now, if we had a false value #f, which was distinct from NIL/(), then
would returning #f be an acceptable substitute to real out-of-band
signalling?

No, because how is a function that is searching for a boolean value
going to indicate the difference between finding #f and not finding an
entry at all?

Unless you can create a completely distinct "false" value for _all_
values, including that "false" value itself[2], you are not going
to be able to avoid conflating some of them.  And that will pose
problems if you insist on in-band signalling (note that in-band- and
out-of-band signalling are usually defined w.r.t. to communication
channels, not w.r.t. distinct alphabets).

So, if you really have to distinguish between "false" and "not found",
or between "empty list" and "not found", use out-of-band signalling,
i.e. use a separate return value for the "found/not found" flag.

That said[3], you will have noticed that empirically, situations where it
is necessary to distinguish between "false" and "not found" don't
arise that often, because false is a common fall-back for "not found"
entries.[4]

The same is in my not-so-very-limited experience true of the empty
list.  It is far more often the case that I _want_ a not-found
situation to degenerate into a "nothing found" <=> "empty list found"
situation.  In a fairly representative sample of 100KLoC of code that
I've written, there are less than 10 occurrences of gethash with a
multiple-value-bind within 2 lines of context (from a total of 373
occurrences of gethash).  And most of those are in an implementation
of weak hash-tables, based on weak references.

Ditto for a random sample of open source CL code, that includes:

- OpenMusic 4.0.3 GPL Release
- cl-http 70.23
- current CMU CL source code, including PCL-derived CLOS, and some
  MIT/Symbolics code

That's a total of around 650KLoC, of very different origins, with
1107 occurrences of gethash.  Of those, there are only 22 occurrences
of m-v-bind within two lines of context, of which probably less than
half are actually uses of m-v-bind on the return value of gethash.

Now, this doesn't necessarily capture all uses of the second return
value of gethash:  it could get passed-through a function return, or
people could use m-v-list, or some other m-v primitive to access the
second value.  Of those only the first case seems to be a common
thing, and even then I'd estimate it not to exceed the direct m-v-bind
scenario.

So even if we round this figure up excessively, we find that this is a
thing that is rarely occurring.  Either people are continuously
writing incorrect code by omitting "required" checks for the second
return value, or, far more likely, they are making good use of the
default value nil/().

Or in other words, CL made certain quite common usage patterns easier
to write and more concise.  It achieved that by making a certain
number of other, less frequent usage patterns more expensive to write.
That seems like a valid trade-off to me.

Of course this doesn't address the issue of the influence of that
design decision on usage patterns.  That said, given that Dylan's
element GF signals an error to indicate "not-found" in its out-of-band
mode, it seems that the designers of Dylan concurred that this is not
a frequent usage pattern, making Dylan an unsuitable target for
further investigation of that issue.

Now that we have thought very hard about this, what are the
conclusions we can draw?  Let's see:

a) CL isn't broken, it made an IMHO valid design trade-off (though it
   probably did so unconsciously).

b) Dylan isn't necessarily broken, it has just made another trade-off,
   and it is for the Dylan community to check whether that trade-off
   paid off in their day-to-day usage.

c) That said, those issues are purely intellectual exercises, because
   neither language community is in any position to revise that
   decision now.

d) When we ever have to design yet another language (i.e. waste
   everybodies time and resources for little gain, instead of
   improving one of the extensible programming languages), it won't be
   because of either choice.  Furthermore, we can't extrapolate from
   either language, because this trade-off will have to be based on
   the interplay with a number of other design decisions, related to
   frequency of use of certain data-structures and constructs.

Regs, Pierre.

Footnotes: 
[1]  It also allows the user to supply another default/not-found value
     instead of NIL/(), which is again a good design decision.

[2]  Which is somewhat problematic to achieve on current day
     computers.

[3]  I.e. having established that your question/problem hasn't really
     been about (eq 'NIL '()) at all.

[4]  This is further mitigated by the fact of footnote [1].

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <871yigaoem.fsf@teonanacatl.andreas.org>
"Pierre R. Mai" <····@acm.org> writes:

> GETHASH is a function that can be employed in situations where an
> empty list, and "didn't find anything" are distinct situations.  Its
> approach is one, that should make Andreas very happy, in that it uses
> true out-of-band signalling to signal the presence or absence of an
> entry, via its second return value.[1]

Actually, it does, it's a nicely designed function.

> [1]  It also allows the user to supply another default/not-found value
>      instead of NIL/(), which is again a good design decision.

I agree.

I think the perfect accessor function would additionally allow for a
third mode of operation: signal a restartable condition.  That would
keep the local code simple (no need to pass around the found/not-found
information) while allowing to handle such a situation.

> Unless you can create a completely distinct "false" value for _all_
> values, including that "false" value itself[2], you are not going
> to be able to avoid conflating some of them.  And that will pose
> problems if you insist on in-band signalling

Again, I agree.

> (note that in-band- and
> out-of-band signalling are usually defined w.r.t. to communication
> channels, not w.r.t. distinct alphabets).

One could argue that bindings, arguments and return values *are*
communication channels.  Anyways, the terms have helped understanding
the nature of the problems involved.

> That's a total of around 650KLoC, of very different origins, with
> 1107 occurrences of gethash.  Of those, there are only 22 occurrences
> of m-v-bind within two lines of context, of which probably less than
> half are actually uses of m-v-bind on the return value of gethash.

Thanks for the statistics.  For comparison, I looked at the Gwydion
Dylan CVS (230KLoC).  I have counted 3594 calls to ELEMENT.  Only 132
of them make use of the default: keyword, so the vast majority is in
situations where unfound elements are considered an unexpected error.
In 108 cases, the default return value is #f.  8 call sites passed
bindings, 4 the empty list, 2 passed zero, 4 some special value like
'\n' or the identity function.  Actually invoking the non-exported
binding trick to avoid the #f collision was necessary in a whopping
six cases.

> So even if we round this figure up excessively, we find that this is a
> thing that is rarely occurring.  Either people are continuously
> writing incorrect code by omitting "required" checks for the second
> return value, or, far more likely, they are making good use of the
> default value nil/().

I think that my numbers show that in the majority of cases the
collection is *known* (or at least strongly suspected) to contain the
element.  In these cases, the check is technically not required, so
nobody could be bothered writing extra code to check it.  However, the
check would definitely help in finding code not behaving like you
think it should, so the exception that's generated is a valuable
debugging aid.

The way it is in CL, I'd expect to see bugs in my code where NIL pops
up in places where I don't expect it, whereas in the same situation in
Dylan I'd get an error message pointing at exactly the place where the
faulty call to ELEMENT is located.

> Of course this doesn't address the issue of the influence of that
> design decision on usage patterns.  That said, given that Dylan's
> element GF signals an error to indicate "not-found" in its out-of-band
> mode, it seems that the designers of Dylan concurred that this is not
> a frequent usage pattern, making Dylan an unsuitable target for
> further investigation of that issue.

Well, see above numbers for how often not-found was actually an
expected outcome and not an error.

> a) CL isn't broken, it made an IMHO valid design trade-off (though it

I have no arguments to dispute that.

> b) Dylan isn't necessarily broken, it has just made another trade-off,
>    and it is for the Dylan community to check whether that trade-off
>    paid off in their day-to-day usage.

Yes, it's pretty convenient to use.  I think it would be even better
if ELEMENT supported a second return value for found/not found, but
that would only very rarely be needed.

> c) That said, those issues are purely intellectual exercises, because
>    neither language community is in any position to revise that
>    decision now.

Yes.  I said I am here to learn something, and I did.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Pierre R. Mai
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87zo54uvje.fsf@orion.bln.pmsf.de>
Andreas Bogk <·······@andreas.org> writes:

> I think the perfect accessor function would additionally allow for a
> third mode of operation: signal a restartable condition.  That would
> keep the local code simple (no need to pass around the found/not-found
> information) while allowing to handle such a situation.

That would have been an interesting possibility, mirroring the
out-of-bounds errors of other collection accessors.  That said, I find
that uses of gethash where the absence of an element are errors are
also situations where it pays to have an abstract accessor function
(or macro), _and_ where it pays to report a more specific error than
"gethash couldn't find an entry in HASHTABLE xxxx for key YYYY".

So I'd write

(defun get-variable-type (variable)
  (or
   (gethash variable *variable-types* nil)
   (error "Can't assign type to unknown variable ~S." variable)))

Or, if the situation is correctable, doing the same with a useful
restart.

> Thanks for the statistics.  For comparison, I looked at the Gwydion
> Dylan CVS (230KLoC).  I have counted 3594 calls to ELEMENT.  Only 132
> of them make use of the default: keyword, so the vast majority is in
> situations where unfound elements are considered an unexpected error.

That is a very interesting statistic, and it probably shows the
influence of language design on usage patterns:  At least for my
personal reference code base, situations where the absence of an entry
in a hash-table directly leads into an "programmer" error situation
are much, much rarer.  The common situations that I can discern (using
examples from our in-house HTTP server) are:

a1) Absence of an entry is to be treated as a useful default value
    (usually nil aka the empty list).  The degeneration is often
    helpful, and sometimes harmless, allowing the base algorithm to be
    simplified.

a2) This often/sometimes occurs in combination with the "intern
    pattern", i.e. an absent value isn't only defaulted on read, the
    key is interned with the default value into the hash-table.

    E.g. interning of HTTP version number objects, which are then used
    in eql-dispatch methods.

b1) Absence of an entry is an error, but not one of program logic,
    rather one of user origin.  So the program will have to deal with
    that situation, create informative error messages, log the
    occurrence, and then signal a very specific condition, that allows
    the user interface code to inform the user in a useful way.

    Consider looking up URLs in a web-servers namespace (though we use
    splay-trees for namespaces, not hash-tables).  You want to signal
    an http-error with :result-code +HTTP-Code-Not-Found+ (or one of
    the related codes, if you know more about the absence), not any
    other error, which will result in an internal server error being
    presented to the user.

    While you could still have gethash signal errors in such a
    situation, which you handled and resignalled as another error,
    this is both much more convoluted and error prone (what if you
    catch an unrelated error, that shouldn't have been so handled?),
    so let's not do this.

b2) Absence of an entry is either a programmer or user error.  But the
    point where the final gethash occurs is so removed from the actual
    source of the problem, that simply signalling an error on the
    gethash is not going to be helpful.  Rather than raising the error
    directly, return a documented invalid value (e.g. nil), and let
    one of the callers that has enough context to give a useful error
    message handle the situation.

    This often occurs in combination with b1, resulting in a1
    behaviour, e.g. namespace-lookup-url returning nil, instead of a
    resource on failed lookups.

c)  Absence of an entry is a direct violation of some invariant, hence
    signalling an error is a good thing to do.

The last case is far and few in-between in my experience, but see
below.

> I think that my numbers show that in the majority of cases the
> collection is *known* (or at least strongly suspected) to contain the
> element.  In these cases, the check is technically not required, so
> nobody could be bothered writing extra code to check it.  However, the
> check would definitely help in finding code not behaving like you
> think it should, so the exception that's generated is a valuable
> debugging aid.

Actually, that is maybe the core of the difference:  Contrary to
e.g. arrays or instances, where I more or less expect the aref or
slot-value/accessor call to succeed, unless I made a mistake
somewhere, I don't think of e.g. alists and has-tables that way.  I
consider those to be dictionary style collections, where the absence
of an entry for a key is to be expected as part of the normal course
of operation, unless I have taken extra measures to ensure the
presence.

It is more like calling information, and inquiring for a phone number,
where failure to get the phone number is a frequent occurrance, and
part of normal operations.

I would guess that this difference in views is at least partly caused
by the behaviour of the two languages default accessors for such data
structures, though it may also be the other way around to some degree.

> The way it is in CL, I'd expect to see bugs in my code where NIL pops
> up in places where I don't expect it, whereas in the same situation in
> Dylan I'd get an error message pointing at exactly the place where the
> faulty call to ELEMENT is located.

While such errors do sometimes happen, you could only cure them by
making the default action of gethash being the error case.  That would
be contrary to current usage patterns (apart from being an incompatible
change), so it would result in lots of "error where none was intended"
bugs in new code in the interim time.

One could instead create a new accessor that defaulted to signalling
an error by default, for people who don't want to think about
non-occurrence.  Whether this would be worth it, considering usage
patterns, the low frequency of such bugs, and the fact that they will
normally be found during testing, because they are natural
border-cases that are included in any serious tests, is another
question.

> Well, see above numbers for how often not-found was actually an
> expected outcome and not an error.

It is my conjecture that the numbers are also influenced by the
design, and not only vice-versa.

> Yes.  I said I am here to learn something, and I did.

In the end, once the questions were properly framed, I found this a
good opportunity to take a more detailed look at usage patterns in CL,
which together with hearing about Dylan usage patterns increased my
understanding of CL usage and the influences of design decisions.  So
I learned something as well.

Regs, Pierre.

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-62A076.15313030112001@news.paradise.net.nz>
Arrrgghh.  I *said* I didn't want to repoen this, and the message to 
which you are replying is part of a meta-discussion.

That said, thank you for your very good summary.  I see little to 
disagree with.


In article <··············@orion.bln.pmsf.de>, "Pierre R. Mai" 
<····@acm.org> wrote:

> Bruce Hoult <·····@hoult.org> writes:
> 
> > The only issue I have, as I said when I joined the thread half a dozen 
> > messages later, is how you tell whether a function searching for a list 
> > and returning it found it and it was empty, or whether it was not found 
> > at all.
> 
> GETHASH is a function that can be employed in situations where an
> empty list, and "didn't find anything" are distinct situations.  Its
> approach is one, that should make Andreas very happy, in that it uses
> true out-of-band signalling to signal the presence or absence of an
> entry, via its second return value.[1]

Yep, GETHASH is perfectly fine.

 
> Now, if we had a false value #f, which was distinct from NIL/(), then
> would returning #f be an acceptable substitute to real out-of-band
> signalling?
> 
> No, because how is a function that is searching for a boolean value
> going to indicate the difference between finding #f and not finding an
> entry at all?

I agree, and I said so in one of my early posts in this thread.  I think 
#f is better than '() for this purpose but it's still not ideal.  It 
should really be a true "bottom" value as used in the likes of ML & 
Haskell.  This I think does solve the conflation problem.

I'll just note that as a matter of usage, it's common in Dylan programs 
to create a custom boolean type using, say, one-of(#"FOO", #"NOT-FOO") 
-- i.e. type-union(singleton(#"FOO"), singleton(#"NOT-FOO")).  It's a 
little more typing than using #t and #f but more self-documenting and 
the efficiency is actually identical, since the <boolean> type is 
defined as one-of(#f, #t) so it's all pointer comparisons anyway.  And 
packed data structures can represent one type-union of two symbols in a 
single bit just as easily as they can represent any other type-union of 
two symbols.


> Or in other words, CL made certain quite common usage patterns easier
> to write and more concise.  It achieved that by making a certain
> number of other, less frequent usage patterns more expensive to write.
> That seems like a valid trade-off to me.

I agree with the principle.


> Of course this doesn't address the issue of the influence of that
> design decision on usage patterns.  That said, given that Dylan's
> element GF signals an error to indicate "not-found" in its out-of-band
> mode, it seems that the designers of Dylan concurred that this is not
> a frequent usage pattern

And the "element" GF also allows you to specify any default value that 
you want, as does CL GETHASH.


> Now that we have thought very hard about this, what are the
> conclusions we can draw?  Let's see:
> 
> a) CL isn't broken, it made an IMHO valid design trade-off (though it
>    probably did so unconsciously).

Sure.

 
> b) Dylan isn't necessarily broken, it has just made another trade-off,
>    and it is for the Dylan community to check whether that trade-off
>    paid off in their day-to-day usage.

Uh huh.

 
> c) That said, those issues are purely intellectual exercises, because
>    neither language community is in any position to revise that
>    decision now.

Maybe, maybe not.  Dylan is a little more likely to be still malleable 
than CL, and there are also new languages popping up that might beneft 
from things learned in both languages.  Curl, for example.  Or Arc, 
which appears to be repeating a *lot* of the design decisions in Dylan, 
while also doing a lot differently.  We haven't seen much of the non 
S-expression grammar yet, but it appears to be going for extreme 
terseness, which the Dylan designers sure didn't do.  There are 
certainly times when "[+ _ 7]" might be more convenient and perhaps 
clearer than either "method(a) a + 7 end" or "(lambda (a) (+ a 7))".  
That's 7 vs 19 vs 20 characters, btw.  Not that brevity is the be all 
and end all.  Dylan is pretty close to my personal lack of brevity limit 
in terms of number of characters, but is perhaps saved because it's not 
that many *tokens*, and also because programs don't require very many 
lines.  COBOL and HyperTalk, on the other hand, are *way* over my lack 
of brevity limit...

-- Bruce
From: Pierre R. Mai
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87vgfsustn.fsf@orion.bln.pmsf.de>
Bruce Hoult <·····@hoult.org> writes:

> Arrrgghh.  I *said* I didn't want to repoen this, and the message to 
> which you are replying is part of a meta-discussion.

While I was aware of that, I got the impression (from the whole
thread, not only from the post I followed up), that the issues I
wanted to put across hadn't been communicated sucessfully, and I also
got the impression that the discussion had been partly about the wrong
thing, so I wanted to clarify some of that.

> That said, thank you for your very good summary.  I see little to 
> disagree with.

So it was worth the effort to reopen this. ;)

> I agree, and I said so in one of my early posts in this thread.  I think 
> #f is better than '() for this purpose but it's still not ideal.  It 
> should really be a true "bottom" value as used in the likes of ML & 
> Haskell.  This I think does solve the conflation problem.

Only if you don't allow that value to escape, e.g. by storing it
somewhere (e.g. in a hash-table), or passing it along.  I rather
prefer the separate return value solution, which is a much more
general solution to the problem of wanting to return more than one
piece of information, than special-casing 

> I'll just note that as a matter of usage, it's common in Dylan programs 
> to create a custom boolean type using, say, one-of(#"FOO", #"NOT-FOO") 
> -- i.e. type-union(singleton(#"FOO"), singleton(#"NOT-FOO")).  It's a 
> little more typing than using #t and #f but more self-documenting and 
> the efficiency is actually identical, since the <boolean> type is 
> defined as one-of(#f, #t) so it's all pointer comparisons anyway.  And 
> packed data structures can represent one type-union of two symbols in a 
> single bit just as easily as they can represent any other type-union of 
> two symbols.

Unless I missed something the types so created are not boolean types,
but rather "binary" types, in that you can't use the usual falseness
tests on them.  That said, using keywords instead of nil and t is a
possible approach in CL, too, although I'd only use it if there was a
better keyword for the non-foo situation than :not-foo.  Otherwise I'd
use :foo and nil.

> And the "element" GF also allows you to specify any default value that 
> you want, as does CL GETHASH.

Yes, I was aware of that, but that wasn't relevant to the point I
wanted to make.

> > c) That said, those issues are purely intellectual exercises, because
> >    neither language community is in any position to revise that
> >    decision now.
> 
> Maybe, maybe not.  Dylan is a little more likely to be still malleable 
> than CL, and there are also new languages popping up that might beneft 

While it might still be more malleable (having only 2-3 common
implementations, and a smaller code base), I'm fairly certain that
changing something as basic as the falseness of empty lists is not
something that would go down well with its user community, unless they
are only in it for the intellectual exercise, which I kind of doubt.

As to new languages popping up, I thought my point d) addressed both
my stance to the usefulness of such things happening, and the
applicability of the particular lessons learned.  The only thing that
designers could take on board from this discusion, IMHO, is that
(projected) usage patterns should influence language design, and
vice-versa, language design will affect usage patterns.  But someone
contemplating designing a new language should have been aware of that
in the first place.

> terseness, which the Dylan designers sure didn't do.  There are 
> certainly times when "[+ _ 7]" might be more convenient and perhaps 
> clearer than either "method(a) a + 7 end" or "(lambda (a) (+ a 7))".  

Very cheap anonymous functions is something that the FP community has
been into for a long time.  It is natural for them to do this,
because they need such functions all over the place, since they have
few other abstraction capabilities.

Having written several KLoC of programs in some of them, I'll make the
following observations:

- Making anonymous functions so cheap can lead to functions becoming
  anonymous, which for documentation purposes alone should have been
  named.

- Such an approach is more suitable in non-interactive languages,
  where not naming functions doesn't affect interactive testability
  (because there is no such thing anyway).

- Together with ubiquitous infix syntax, ubiquitous function
  overloading based on argument types, and a mathematical bent, such
  things can quickly lead to programs becoming as readable as basic
  lambda calculus:

FUN <* : set[map[alpha,lessa,beta],lessm] ** 
         set[map[alpha,lessa,beta],lessm] -> 
         set[map[alpha,lessa,beta],lessm]
DEF sm1 <* sm2 == 
        flat((\\ i . ((\\ j . i <+ j) * sm2)) * sm1)

FUN search: 
     (alpha ** beta -> bool) -> 
     (alpha ** beta -> alpha ** beta -> bool) -> 
     set[alpha,lessa] ** set[beta,lessb] -> 
     set[map[alpha,lessa,beta],lessm]

DEF search(pointwisea)(mutuallya)(setAlpha,setBeta) ==
  IF {}?(setAlpha) THEN {}'Set[map[alpha,lessa,beta],lessm]
  ELSE
  LET
    a == arb(setAlpha)
    fsearch == search(pointwisea)(mutuallya)(setAlpha - %(a), setBeta)
    b_in_B == (\\ n. pointwisea(a, n)) | setBeta
  IN
  flat((\\ b . 
        ((\\ fs_map . 
          pw(mutuallya(a,b))(fs_map))| fsearch) <* %(def(a,b,{}))) * b_in_B)
  FI

This implements generic pointwise global search.  Totally cool that it
can be sculpted with such succinctness.  When writing such code, you
are in a state of mind that is more like creating a proof than writing
a novel.  It is exhilerating when (after several hours) you have
gotten your 100 line program to type-check, which usually means it
will work for the cases you are interested in.  Enjoy that feeling,
walk away and never return to that program.  You will not be able to
understand your own program without investing nearly the same amount
of time that you did while writing it.  Others will be able to work
through your proof^Wprogram, if they invest the required time.  Don't
even think about changing one of the assumptions your program is based
on, without all hell breaking lose.

[ Note that OPAL -- the language in question -- also allows anonymous
 functions to be specified using anonymous parameters, like the Arc
 example  above, e.g. _ + 5.  Haskell throws automatic currying support
 into the mix, which OPAL avoids. ]

While I sometimes long for the brevity of \\x.2*x, or the automatic
currying support, I don't think such features come without serious
downsides.

Regs, Pierre.

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-AA739D.16402601122001@news.paradise.net.nz>
In article <··············@orion.bln.pmsf.de>, "Pierre R. Mai" 
<····@acm.org> wrote:

> > I'll just note that as a matter of usage, it's common in Dylan programs 
> > to create a custom boolean type using, say, one-of(#"FOO", #"NOT-FOO") 
> > -- i.e. type-union(singleton(#"FOO"), singleton(#"NOT-FOO")).  It's a 
> > little more typing than using #t and #f but more self-documenting and 
> > the efficiency is actually identical, since the <boolean> type is 
> > defined as one-of(#f, #t) so it's all pointer comparisons anyway.  And 
> > packed data structures can represent one type-union of two symbols in a 
> > single bit just as easily as they can represent any other type-union of 
> > two symbols.
> 
> Unless I missed something the types so created are not boolean types,
> but rather "binary" types, in that you can't use the usual falseness
> tests on them.

Right.  That's why I said that it's a little more typing -- you have to 
use if(x = foo:) instead of if(x).


> That said, using keywords instead of nil and t is a
> possible approach in CL, too, although I'd only use it if there was a
> better keyword for the non-foo situation than :not-foo.

Agreed.


> > terseness, which the Dylan designers sure didn't do.  There are 
> > certainly times when "[+ _ 7]" might be more convenient and perhaps 
> > clearer than either "method(a) a + 7 end" or "(lambda (a) (+ a 7))".  
> 
> Very cheap anonymous functions is something that the FP community has
> been into for a long time.  It is natural for them to do this,
> because they need such functions all over the place, since they have
> few other abstraction capabilities.

True.


> This implements generic pointwise global search.  Totally cool that it
> can be sculpted with such succinctness.  When writing such code, you
> are in a state of mind that is more like creating a proof than writing
> a novel.  It is exhilerating when (after several hours) you have
> gotten your 100 line program to type-check, which usually means it
> will work for the cases you are interested in.  Enjoy that feeling,
> walk away and never return to that program.  You will not be able to
> understand your own program without investing nearly the same amount
> of time that you did while writing it.

This is also true of many programs in C++ and Perl, though without the 
expressive power.


> While I sometimes long for the brevity of \\x.2*x, or the automatic
> currying support, I don't think such features come without serious
> downsides.

Automatic currying scares me.  It's handy to just be able to write "+ 1" 
(or more likely "(+ 1)") but you can't ask "how many arguments does this 
function take?".  One, of course.  And it returns a function which takes 
an argument and returns a function that takes an argument and returns a 
function that takes an argument and returns an integer.  So the answer 
I'm really interested in with that question is "4".  "How many arguments 
before w get a return value that isn't a function".

I'm not sure that most people are ready for that :-)

-- Bruce
From: Brian P Templeton
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87bsgqyjto.fsf@tunes.org>
"Pierre R. Mai" <····@acm.org> writes:

> Bruce Hoult <·····@hoult.org> writes:
> 
[...]
>> I'll just note that as a matter of usage, it's common in Dylan programs 
>> to create a custom boolean type using, say, one-of(#"FOO", #"NOT-FOO") 
>> -- i.e. type-union(singleton(#"FOO"), singleton(#"NOT-FOO")).  It's a 
>> little more typing than using #t and #f but more self-documenting and 
>> the efficiency is actually identical, since the <boolean> type is 
>> defined as one-of(#f, #t) so it's all pointer comparisons anyway.  And 
>> packed data structures can represent one type-union of two symbols in a 
>> single bit just as easily as they can represent any other type-union of 
>> two symbols.
> 
> Unless I missed something the types so created are not boolean types,
> but rather "binary" types, in that you can't use the usual falseness
> tests on them.  That said, using keywords instead of nil and t is a
> possible approach in CL, too, although I'd only use it if there was a
> better keyword for the non-foo situation than :not-foo.  Otherwise I'd
> use :foo and nil.
> 
I'd use :foo and (not :foo). (IIRC, that suggestion was originally
from some Emacs Lisp programming style suggestions in Jari Aalto's
Tiny Tools package.)

[...]

-- 
BPT <···@tunes.org>	    		/"\ ASCII Ribbon Campaign
backronym for Linux:			\ / No HTML or RTF in mail
	Linux Is Not Unix			 X  No MS-Word in mail
Meme plague ;)   --------->		/ \ Respect Open Standards
From: Christopher Stacy
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <u7ks850da.fsf@spacy.Boston.MA.US>
>>>>> On 30 Nov 2001 05:11:29 +0100, Andreas Bogk ("Andreas") writes:
 Andreas> The way it is in CL, I'd expect to see bugs in my code where NIL pops
 Andreas> up in places where I don't expect it, whereas in the same situation in
 Andreas> Dylan I'd get an error message pointing at exactly the place where the
 Andreas> faulty call to ELEMENT is located.

In the situations where NIL is an incorrect value, writing the code
to check for that is going to be about the same as having made some
kind of type declarations for it.  When there's a stray NIL about, 
it doesn't take very long for it to get used in some very inappropriate
way (such as being function called, or as an argument of the wrong type).  
Using interactive debugging facilities, it doesn't take very long to
find the proximal problem before you can proceed to the underlying bug.
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfw4rncbv0v.fsf@shell01.TheWorld.com>
Christopher Stacy <······@spacy.Boston.MA.US> writes:

> >>>>> On 30 Nov 2001 05:11:29 +0100, Andreas Bogk ("Andreas")
>  Andreas> writes: The way it is in CL, I'd expect to see bugs in my
>  Andreas> code where NIL pops up in places where I don't expect it,
>  Andreas> whereas in the same situation in Dylan I'd get an error
>  Andreas> message pointing at exactly the place where the faulty
>  Andreas> call to ELEMENT is located.
> 
> In the situations where NIL is an incorrect value, writing the code
> to check for that is going to be about the same as having made some
> kind of type declarations for it.  When there's a stray NIL about, 
> it doesn't take very long for it to get used in some very inappropriate
> way (such as being function called, or as an argument of the wrong type).  
> Using interactive debugging facilities, it doesn't take very long to
> find the proximal problem before you can proceed to the underlying bug.

Upon reading Chris's remark, I suddenly had the following epiphany:

Is the reason that people focus so much on static type checking that it's
so hard to get a program to RUN in those languages?  In CL, you can run a
partial program immediately upon writing it, and we often do.  So in those
other programs, one runs the compiler to find errors on the basis of "static"
info.  Whereas in CL you often also run a program fragment.  In a language
that makes you wait longer to test your code, perhaps the sense of need
for static typechecking is higher, since that's all you can get for a long
time...
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3216096657595675@naggum.net>
* Kent M Pitman
| Is the reason that people focus so much on static type checking that it's
| so hard to get a program to RUN in those languages?  In CL, you can run a
| partial program immediately upon writing it, and we often do.  So in
| those other programs, one runs the compiler to find errors on the basis
| of "static" info.  Whereas in CL you often also run a program fragment.
| In a language that makes you wait longer to test your code, perhaps the
| sense of need for static typechecking is higher, since that's all you can
| get for a long time...

  Interesting perspective.  If a CL program omits a function definition,
  the debugger is invoked when it is called, and one may usually define it
  and try the calling form again, even when the caller is compiled.  If a
  function in a static language program is omitted, there has traditionally
  _not_ been a debugger to invoke because the debugger or any other part of
  the development environment are not part of the "executable", so what do
  you do?  You could just terminate with a linking error, but that would
  only be marginally more useful than having the compiler gripe about it --
  and it is easy enough to write your own "stub function" that signals the
  absence of a real function body.  How useful would a debugger be for a
  language that forces the programmer to recompile a large number of its
  source files if you made changes?

  The choice to use as much as possible of the available information from
  the compilation process in the _caller_, instead of in the _callee_, may
  account for more of the difference between languages than the static vs
  dynamic nature of its type system, since that appears to be the fall-out
  of the former choice, not fundamental to it, as the more you (want to)
  optimize the _user_ of any object, the more static the whole language has
  to be.  However, as more and more information becomes available and is
  known to be static, more and more of it _may_ be used in the caller.
  This is probably also why declarations in static languages are promises
  that are required, yet expected to be broken, so the compiler punishes
  you when you do have lied (the IRS model of honesty), while they are
  (optional) promises that are expected to be kept in Common Lisp (the
  family model of honesty).

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Tim Bradshaw
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <fbc0f5d1.0111300823.120843d4@posting.google.com>
Erik Naggum <····@naggum.net> wrote in message news:<················@naggum.net>...
> 
>   Interesting perspective.  If a CL program omits a function definition,
>   the debugger is invoked when it is called, and one may usually define it
>   and try the calling form again, even when the caller is compiled.  If a
>   function in a static language program is omitted, there has traditionally
>   _not_ been a debugger to invoke because the debugger or any other part of
>   the development environment are not part of the "executable", so what do
>   you do?  You could just terminate with a linking error, but that would
>   only be marginally more useful than having the compiler gripe about it --
>   and it is easy enough to write your own "stub function" that signals the
>   absence of a real function body.  How useful would a debugger be for a
>   language that forces the programmer to recompile a large number of its
>   source files if you made changes?

Another take on debuggers is that in static languages it is *hugely*
more important to have a hairy debugger with stepping features than in
Lisp, because the time from one working version to another, even if
you only change a line, is minutes at least because of the hairy link
cycles (and elaborate dependency stuff in the build system.  So while
a Lisp debugger's basic task is to tell you where you are and point
the editor at the bad bit of code, and then to let you restart the
call with now-redefined code with suitable print statements or
whatever (redefinition having taken several milliseconds), a
static-language debugger needs to help you make an exhaustive analysis
of the problem because any fix, no matter how small, is going to take
minutes or hours.

--tim
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwpu60dveu.fsf@shell01.TheWorld.com>
··········@tfeb.org (Tim Bradshaw) writes:

> Another take on debuggers is that in static languages it is *hugely*
> more important to have a hairy debugger with stepping features than in
> Lisp,

Nah. I don't use 'em.  I just use print statements.  What makes Java a win
is that they didn't make "does output to standard-output" part of the type
signature.  If adding debuggging statements were considered a change of
signature, which arguably they should be in a language like Java that wants
to statically check everything in advance, it would be impossible for me to
debug anything. ;)
From: Florian Weimer
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87snavymjy.fsf@deneb.enyo.de>
Kent M Pitman <······@world.std.com> writes:

> If adding debuggging statements were considered a change of
> signature, which arguably they should be in a language like Java
> that wants to statically check everything in advance, it would be
> impossible for me to debug anything. ;)

Therefore, in Ada, it's quite a challenge to debug pure library units
(which may not depend on other library units which may have side
effects, such as output).  People work around this limitation by using
pragma Import/Export, completely bypassing type safety, elaboration
checking and what else. ;-)
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwitbrh80f.fsf@shell01.TheWorld.com>
Bruce Hoult <·····@hoult.org> writes:

> In article <····························@posting.google.com>, 
> ··········@tfeb.org (Tim Bradshaw) wrote:
> 
> > Another take on debuggers is that in static languages it is *hugely*
> > more important to have a hairy debugger with stepping features than in
> > Lisp, because the time from one working version to another, even if
> > you only change a line, is minutes at least because of the hairy link
> > cycles (and elaborate dependency stuff in the build system.
> 
> To be fair to them, I haven't had static language turn-around times of 
> anything *like* that since CodeWarrior came out on the first PowerMacs.  
> Prior to that, with MPW on 68k machines, it was pretty common to have 
> multi-minute cycle times on single line changes (and half an hour to 
> recompile the whole MacApp library), but as soon as CodeWarrior+60MHz 
> PPC appeared it took less than two minutes to recompile MacApp and 
> seconds to compile&go after a one line change in an implementation file.

Assuming there is a compiled app to go to.

I was more comparing to starting off with something like:

 (defun my-quicken-pro ()
   (call-tool (select-tool)))

and then usefully doing:

 (my-quicken-pro)

Sure, you end up in the debugger REALLY fast, but you can tell where you are
in the program and you can return values.  You can write substitute code from
there and proceed your application.  And the debugging state you get while
you're poking around is as meaningful as it would be in a complete app.

Other languages would really have no meaning to calling a program like this
that was just a fragment.  Sure, once the tool is developed, with both 
incremental and fast compilation, it can be fixed and started.  But during
evolution, wanting to test a tool out of context, most languages don't have a
meaning to data independent of app, how to view it, how to type it, etc.
Yes, if it operates on data files, sometimes you can make a standalone app
that runs on a test data file and then quits, but that's about it.

Lisp isn't alone in having this capability.  But languages like Java, C++,
and C don't seem to have it in the implementations I've seen.
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcvk7w7e6zk.fsf@conquest.OCF.Berkeley.EDU>
Kent M Pitman <······@world.std.com> writes:

> Lisp isn't alone in having this capability.  But languages like Java, C++,
> and C don't seem to have it in the implementations I've seen.

Interestingly, I think GNU C was supposed to have this capability, via
a C interpreter in the debugger, but no one ever finished it.  Now
*that* would have made for a nicer environment.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-41D4F0.16525501122001@news.paradise.net.nz>
In article <····························@posting.google.com>, 
··········@tfeb.org (Tim Bradshaw) wrote:

> Another take on debuggers is that in static languages it is *hugely*
> more important to have a hairy debugger with stepping features than in
> Lisp, because the time from one working version to another, even if
> you only change a line, is minutes at least because of the hairy link
> cycles (and elaborate dependency stuff in the build system.

To be fair to them, I haven't had static language turn-around times of 
anything *like* that since CodeWarrior came out on the first PowerMacs.  
Prior to that, with MPW on 68k machines, it was pretty common to have 
multi-minute cycle times on single line changes (and half an hour to 
recompile the whole MacApp library), but as soon as CodeWarrior+60MHz 
PPC appeared it took less than two minutes to recompile MacApp and 
seconds to compile&go after a one line change in an implementation file.

-- Bruce
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcv3d2vvaa7.fsf@whirlwind.OCF.Berkeley.EDU>
Bruce Hoult <·····@hoult.org> writes:

> In article <····························@posting.google.com>, 
> ··········@tfeb.org (Tim Bradshaw) wrote:
> 
> > Another take on debuggers is that in static languages it is *hugely*
> > more important to have a hairy debugger with stepping features than in
> > Lisp, because the time from one working version to another, even if
> > you only change a line, is minutes at least because of the hairy link
> > cycles (and elaborate dependency stuff in the build system.
> 
> To be fair to them, I haven't had static language turn-around times of 
> anything *like* that since CodeWarrior came out on the first PowerMacs.  
> Prior to that, with MPW on 68k machines, it was pretty common to have 
> multi-minute cycle times on single line changes (and half an hour to 
> recompile the whole MacApp library), but as soon as CodeWarrior+60MHz 
> PPC appeared it took less than two minutes to recompile MacApp and 
> seconds to compile&go after a one line change in an implementation file.

This is true for small things.  Large systems continue to grow, and
I've worked on a project where it wasn't unusual for a one-line change
to require 90 minutes of recompilation (if it was a one-line change in
the right module).

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Kenny Tilton
Subject: C++ cycle time
Date: 
Message-ID: <3C0870C7.93156997@nyc.rr.com>
"Thomas F. Burdick" wrote:
> 
> This is true for small things.  Large systems continue to grow, and
> I've worked on a project where it wasn't unusual for a one-line change
> to require 90 minutes of recompilation (if it was a one-line change in
> the right module).
> 

Criminy o' golden!

Does that mean the XP crowd does not use C++? They go on about
refactoring, and indeed that is a Good Thing, lets you keep moving
towards The Light. I am forever changing data structures, juggling
inheritance, yada yada.

I guess big C++ projects spend more time thinking and planning and less
time tossing code around?

kenny
clinisys
From: Thomas F. Burdick
Subject: Re: C++ cycle time
Date: 
Message-ID: <xcvoflje73t.fsf@conquest.OCF.Berkeley.EDU>
Kenny Tilton <·······@nyc.rr.com> writes:

> "Thomas F. Burdick" wrote:
> > 
> > This is true for small things.  Large systems continue to grow, and
> > I've worked on a project where it wasn't unusual for a one-line change
> > to require 90 minutes of recompilation (if it was a one-line change in
> > the right module).
> > 
> 
> Criminy o' golden!
> 
> Does that mean the XP crowd does not use C++? They go on about
> refactoring, and indeed that is a Good Thing, lets you keep moving
> towards The Light. I am forever changing data structures, juggling
> inheritance, yada yada.

I've gotten the impression that Real XP Types use SmallTalk.  I'm sure
C++ types "do" XP, but they "do" a lot of things with about the same
level of success.

> I guess big C++ projects spend more time thinking and planning and less
> time tossing code around?

It depends, I think.  In my experience, you sometimes go the
"rapid"[*] prototype -> complete rewrite -> incremental changes route;
but sometimes you're forced to do Lots Of Careful Planning.  It all
depends on what part of the dependency graph you're working on, and
how good your Makefiles are.  Incidentally, I wasn't very good at
Makefiles until I worked on a large C++ project.  Making full use of
the GNU Makefile language was *vital* to my ability to write any
amount of code, because a naive build system would have sent me into
unnecessary Recompilation Hell.

[*] Scare quotes to indicate this is only true for C++ values of
"rapid," which have no realationship to the Lisp value of the same
name.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Erik Naggum
Subject: Re: C++ cycle time
Date: 
Message-ID: <3216201163137950@naggum.net>
* Kenny Tilton
| I guess big C++ projects spend more time thinking and planning and less
| time tossing code around?

  It appears to me that big C++ projects only actually work well if they
  "lucked out" with their design early enough to avoid rethinking it.  If
  not, they die.  When you have precise knowledge of the problem domain and
  you are able to anticipate your requirements completely, C++ is not a bad
  choice of language.  This implies that the thinking and planning stage
  must have started a long time before anyting actually start thinking and
  planning for a particular project -- only if you do _not_ have to make
  engineering decisions during the course of development does it make sense
  to use C++.  This contributes to the need for patterns and "patterns" in
  C++ software development, and especially of avoiding questioning the way
  things are done, which means good leadership and loyal team members.

  But more than software problems, I think C++ produces social problems and
  requires harsh solutions to them.  I and others have been arguing for a
  long time that there is no one unique right solution to a problem without
  a context and that there are tradeoffs between all kinds of factors
  depending on the context, and that allowing the "rightest" solution to
  emerge as sufficient knowledge to make the best tradeoffs emerges, is the
  only way to make those tradeoffs.  If this is to succeed in a brittle and
  frail language as C++, _people_ have to agree, or not be allowed to have
  any "ideas" of their own about what is right to do.  In my view, C++ is a
  good language if you have a benevolent dictator and people who are
  willing to accept orders from above down to the very tiniest details.  In
  other words, C++ is an excellent assembly-line programming language.

  I think the kinds of problems that can be solved successfully in C++ are
  limited by the mental capacity of the leading designer.  Abstraction in
  the language is not necessary, as it is cheaper to pay people to do the
  menial labor of typing in a lot of code than to design with the right
  abstractions, and this seems to account for the low abstracation level in
  successful and large C++ projects.  This also leads to the development of
  other languages and tools to manage all the abstraction that is not to
  occur in C++, because it is impossible to think design in C++ due to the
  immense cognitive load of the language.  If designing software is like
  building a mechanical clock, it does nobody any good to have to do it
  moleculy by molecule.

  The reason I made up my mind never to use C++ again when a project died
  on me back in 1994, was primarily that the information required for any
  particular decision is not available until a long time after it must be
  made.  Now, dealing with uncertain information is no big deal by itself,
  but the process of discovery of the required certainty is very expensive
  in C++, and if you are fully aware of the decisions you make on missing
  or insufficient information, the "backtrack log" grows much faster than
  your "progress log", and if you are not aware of the decisions you make,
  you will go seriously wrong.  This is not unlike those people we see come
  to comp.lang.lisp who base most of their opinions about (Common) Lisp on
  guesswork and who refuse to question the assumptions on which they have
  built their current set of conclusions, and who, amazingly, think they
  are still as certain in their conclusions as they were with the little
  bit of fact that they once acquired.  Some people just _have_ to fill in
  the blanks between the things they are certain about and are probably not
  even aware of this seriously bad mental habit.  This does not work well
  in programming in general, but C++ is a language that really punishes you
  for this kind of mistake, while it makes avoiding it and doing things
  right is prohibitively expensive.

  My conclusion is that C++ is not a language that _can_ be used by very
  intelligent people -- it requires that you _not_ think carefully about
  what you do -- but rather suitable for people who can tolerate a lot of
  failure.  Likes sales people who continue to have a great attitude even
  though they get 99% rejections, I imagine that good C++ programmers must
  tolerate doing _so_ much manual work, and repeating it several times,
  which would tell me that I am doing something seriously wrong and quit
  and find something else to do.  ... which I did.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Kenny Tilton
Subject: Re: C++ Cycle times [Was: Re: On nil qua false]
Date: 
Message-ID: <3C0857B5.CEB8ECE7@nyc.rr.com>
I have been curious about current cycle times in the land of C++, been a
long time for me. I do remember the transition from Think's C+- which
still managed incremental linking to Symantec C++ which gave up on that.
I was very depressed by that.

Bruce Hoult wrote:
>  but as soon as CodeWarrior+60MHz
> PPC appeared it took less than two minutes to recompile MacApp and
> seconds to compile&go after a one line change in an implementation file.

What is it like now with today's clock speeds, on PPC or Intel? I mean a
nice fat 100k LOC app. I gather it's uglier if you change a key header
file, so maybe two values: one for a key header used ubiquitously and
one for a single non-header file, say to add a debugging print
statement.

And is every link from scratch? Or are they able to save some work on a
re-link?

thx,

kenny
clinisys
From: John Markus Bjorndalen
Subject: Re: C++ Cycle times [Was: Re: On nil qua false]
Date: 
Message-ID: <hvu1vbdy5h.fsf@johnmnb.cs.uit.no>
Kenny Tilton <·······@nyc.rr.com> writes:

> What is it like now with today's clock speeds, on PPC or Intel? I mean a
> nice fat 100k LOC app. I gather it's uglier if you change a key header
> file, so maybe two values: one for a key header used ubiquitously and
> one for a single non-header file, say to add a debugging print
> statement.

Just to give you an example from simpler applications: Compiling a
100-line file using wxWindows or with a hardware simulation library
for C++ (I forgot the name and I really don't want to remember it
either) would take around 10 seconds on a 650MHz PIII. Change a line
in a header file or do some rearranging of code and you quickly start
measuring recompile time in minutes even for very small projects.

And then you link the compiled object files... 

-- 
	// John Markus Bj�rndalen
From: Duane Rettig
Subject: Re: C++ Cycle times [Was: Re: On nil qua false]
Date: 
Message-ID: <4zo52rjy2.fsf@beta.franz.com>
John Markus Bjorndalen <·····@cs.uit.no> writes:

> Kenny Tilton <·······@nyc.rr.com> writes:
> 
> > What is it like now with today's clock speeds, on PPC or Intel? I mean a
> > nice fat 100k LOC app. I gather it's uglier if you change a key header
> > file, so maybe two values: one for a key header used ubiquitously and
> > one for a single non-header file, say to add a debugging print
> > statement.
> 
> Just to give you an example from simpler applications: Compiling a
> 100-line file using wxWindows or with a hardware simulation library
> for C++ (I forgot the name and I really don't want to remember it
> either) would take around 10 seconds on a 650MHz PIII. Change a line
> in a header file or do some rearranging of code and you quickly start
> measuring recompile time in minutes even for very small projects.
> 
> And then you link the compiled object files... 

Don't forget also that you also have to set up your application's
environment again, which was lost when you had to restart it.  In
a non-trivial application with lots of file accessing and cache building,
this can be nontrivial.

-- 
Duane Rettig          Franz Inc.            http://www.franz.com/ (www)
1995 University Ave Suite 275  Berkeley, CA 94704
Phone: (510) 548-3600; FAX: (510) 548-8253   ·····@Franz.COM (internet)
From: Jens Kilian
Subject: Re: C++ Cycle times [Was: Re: On nil qua false]
Date: 
Message-ID: <sfvgfnoy90.fsf@bstde026.germany.agilent.com>
Duane Rettig <·····@franz.com> writes:
> Don't forget also that you also have to set up your application's
> environment again, which was lost when you had to restart it.  In
> a non-trivial application with lots of file accessing and cache building,
> this can be nontrivial.

The first "real" application I worked on had start-up times upwards of
30 minutes.  Most of that was due to a user interface written in interpreted
Lisp.

Five minutes after starting, it would crash (in the C++ part ;-)

Things got better when we started compiling the Lisp code...
-- 
··········@acm.org                 phone:+49-7031-464-7698 (TELNET 778-7698)
  http://www.bawue.de/~jjk/          fax:+49-7031-464-7351
PGP:       06 04 1C 35 7B DC 1F 26 As the air to a bird, or the sea to a fish,
0x555DA8B5 BB A2 F0 66 77 75 E1 08 so is contempt to the contemptible. [Blake]
From: Bruce Hoult
Subject: Re: C++ Cycle times [Was: Re: On nil qua false]
Date: 
Message-ID: <bruce-DE84BE.09460102122001@news.paradise.net.nz>
In article <··············@johnmnb.cs.uit.no>, John Markus Bjorndalen 
<·····@cs.uit.no> wrote:

> Kenny Tilton <·······@nyc.rr.com> writes:
> 
> > What is it like now with today's clock speeds, on PPC or Intel? I mean a
> > nice fat 100k LOC app. I gather it's uglier if you change a key header
> > file, so maybe two values: one for a key header used ubiquitously and
> > one for a single non-header file, say to add a debugging print
> > statement.
> 
> Just to give you an example from simpler applications: Compiling a
> 100-line file using wxWindows or with a hardware simulation library
> for C++ (I forgot the name and I really don't want to remember it
> either) would take around 10 seconds on a 650MHz PIII. Change a line
> in a header file or do some rearranging of code and you quickly start
> measuring recompile time in minutes even for very small projects.
> 
> And then you link the compiled object files...

My current project is porting a 400k line C++ program from Windows to 
MacOS X and Linux.  If I make a change in a typical implementation file 
and hit "run" in VC++ it takes 2 - 3 seconds before I'm up and running 
in the program.  This on a PIII/1000.

Of course it is several minutes if you change something in a 
heavily-used header file.

-- Bruce
From: John Markus Bjorndalen
Subject: Re: C++ Cycle times [Was: Re: On nil qua false]
Date: 
Message-ID: <hvd71yeduh.fsf@johnmnb.cs.uit.no>
Bruce Hoult <·····@hoult.org> writes:

> My current project is porting a 400k line C++ program from Windows to 
> MacOS X and Linux.  If I make a change in a typical implementation file 
> and hit "run" in VC++ it takes 2 - 3 seconds before I'm up and running 
> in the program.  This on a PIII/1000.

Using precompiled header files I would assume :) 

That's one of the things that the Windows C++ compilers seemed to
quickly have a need for (and thus implemented). A C++ file with just a
few of the standard "C-type" includes should compile quickly even
without precompiled header files. It seems like the number of lines in
your project has less to do with the compile time than the selection
of include files and frameworks you choose to use.

Precompiled header files is definitely an advantage at times, but I
suspect that it can be a bit difficult maintaining them in a
consistent way. It is not _that_ uncommon to experience different
results if header files are included in different orders in the source
files for instance.

What got me a little suspicious about the idea was that VC++ seemed to
mess up it's own precompiled header files a few years ago resulting in
mysterious behaviour in the executable files. The simple fix was to
remove everything the compiler had generated (simply doing 'rebuild
all' did not help) and recompile, but the bad part of it (apart from
the annoyance and wasted time) was that I didn't really trust the
compiler after that.

On the other hand, I haven't experienced this problem with the latest
service packs (not that I have used the compiler that much lately).
 
> Of course it is several minutes if you change something in a 
> heavily-used header file.

Yes :-/

-- 
	// John Markus Bj�rndalen
From: Wade Humeniuk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <9uatbj$9va$1@news3.cadvision.com>
> To be fair to them, I haven't had static language turn-around times of
> anything *like* that since CodeWarrior came out on the first PowerMacs.
> Prior to that, with MPW on 68k machines, it was pretty common to have
> multi-minute cycle times on single line changes (and half an hour to
> recompile the whole MacApp library), but as soon as CodeWarrior+60MHz
> PPC appeared it took less than two minutes to recompile MacApp and
> seconds to compile&go after a one line change in an implementation file.

There is not just the turn around time in a compile and link, but actually
running the code to where the error occurs again.  The same sequence of
actions usually has to be recreated.  This may take a while.  (Say a
protoocl error between two apps).  The setup time to run the code can be
very prohibitive.

Wade
From: Paolo Amoroso
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <6I0HPMvk0tTVFu9epjOGA7OXWLU=@4ax.com>
On Fri, 30 Nov 2001 08:11:00 GMT, Erik Naggum <····@naggum.net> wrote:

>   Interesting perspective.  If a CL program omits a function definition,
>   the debugger is invoked when it is called, and one may usually define it
>   and try the calling form again, even when the caller is compiled.  If a

Or maybe return the value expected from the called function without even
defining it.


Paolo
-- 
EncyCMUCLopedia * Extensive collection of CMU Common Lisp documentation
http://web.mclink.it/amoroso/ency/README
[http://cvs2.cons.org:8000/cmucl/doc/EncyCMUCLopedia/]
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-A8BAC4.20223730112001@news.paradise.net.nz>
In article <···············@shell01.TheWorld.com>, Kent M Pitman 
<······@world.std.com> wrote:

> Christopher Stacy <······@spacy.Boston.MA.US> writes:
> 
> > >>>>> On 30 Nov 2001 05:11:29 +0100, Andreas Bogk ("Andreas")
> >  Andreas> writes: The way it is in CL, I'd expect to see bugs in my
> >  Andreas> code where NIL pops up in places where I don't expect it,
> >  Andreas> whereas in the same situation in Dylan I'd get an error
> >  Andreas> message pointing at exactly the place where the faulty
> >  Andreas> call to ELEMENT is located.
> > 
> > In the situations where NIL is an incorrect value, writing the code
> > to check for that is going to be about the same as having made some
> > kind of type declarations for it.  When there's a stray NIL about, 
> > it doesn't take very long for it to get used in some very inappropriate
> > way (such as being function called, or as an argument of the wrong 
> > type).  
> > Using interactive debugging facilities, it doesn't take very long to
> > find the proximal problem before you can proceed to the underlying bug.
> 
> Upon reading Chris's remark, I suddenly had the following epiphany:
> 
> Is the reason that people focus so much on static type checking that it's
> so hard to get a program to RUN in those languages?  In CL, you can run a
> partial program immediately upon writing it, and we often do.  So in 
> those
> other programs, one runs the compiler to find errors on the basis of 
> "static"
> info.  Whereas in CL you often also run a program fragment.  In a 
> language
> that makes you wait longer to test your code, perhaps the sense of need
> for static typechecking is higher, since that's all you can get for a 
> long time..

That's certainly what the Smalltalk XP people say.

On the other hand, testing can only show that there are no errors for 
the data that you tested on, not for *every* possible run.

On the gripping hand, in an interactive environment you can easily set 
up tests for code paths that are "never supposed to happen", which migth 
be very very hard to test in a batch environement.

-- Bruce
From: Alain Picard
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <86lmgovbhx.fsf@gondolin.local.net>
Kent M Pitman <······@world.std.com> writes:

> Is the reason that people focus so much on static type checking that it's
> so hard to get a program to RUN in those languages?  

Yes.

It's also the reason those people have such a hard time with XP�:
They say "why write all those unit tests? The _compiler_ can do
all that checking for you!"

They miss the point that the unit tests check the _semantics_ of
the functions/data/arguments, whatever, which usually 

a) makes you think about your function harder when you design the test
b) lets you check types, if that's relevant (e.g. if the method is
   a CLOS method specialized on something, well, you don't need typechecking.
   You'll get a "no such method" error.
c) It's not a lot harder to write a unit test and to get it to run in
   a dynamic environment like CL or smalltalk than it is to fight the compiler 
   until it blesses your program.  The test, however, remains forever, can
   be refactored, used as documentation for the method, etc etc.

I've had this fight many, many times.

The other main reason people love static type checking is they somehow
think it makes their programs safer.  (I kid you not).  Core dumps obviously
don't count.

I conclude from this that a large part of the IT industry is in total denial.



� XP grew up in smalltalk

-- 
It would be difficult to construe        Larry Wall, in  article
this as a feature.			 <·····················@netlabs.com>
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87elmg8l6j.fsf@teonanacatl.andreas.org>
Christopher Stacy <······@spacy.Boston.MA.US> writes:

> Using interactive debugging facilities, it doesn't take very long to
> find the proximal problem before you can proceed to the underlying bug.

I would have expected that as well :).

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215957794156875@naggum.net>
* Bruce Hoult
| Of course you'd hav to ask him to find out, but I suspect that he's been
| seeking a wider audience for his ideas, as first developed in the
| various "lambda the ultimate ..." papers and no doubt refined since.

  _I_ assume that Guy L. Steele is a very smart _professional_ and is not
  married to any of the languages on which he has worked.  Actually, I do
  not expect a _personal_ attachment from any seriously good Common Lisp
  programmer.  There are personal _values_, but they can and should be
  approached professionally, because one cannot always get what one wants,
  and it is incredibly stupid to whine for decades about something you did
  not get that was personal to you.

  The distinction between personal and professional seems to be lost on
  some people.  They tend to get into problems when they are required to be
  professional and detach personally.

| That applies in both directions, though you wouldn't know it to read 
| many of the replies to myself and Andreas here.

  Of course you are the judge of this, because you have already made up
  your mind and you also get personal about it, so you are prevented from
  seeing the _professionalism_ in the replies you get.

| And Andreas and I have much the same subtly different connotation.  The
| only real difference is that we think that perpetuating the old "the
| list is the fundamental datastructure in Lisps" myth is doing the Lisp
| community (of which we are a part) a disservice.

  Why have you decided to find converts in comp.lang.lisp?  This looks more
  and more like a personal mission.  Invite those who want to discuss this
  stupid shit with you to comp.lang.dylan.  It does not look like anybody
  would disturb anyone.

| We want to be able to use the *same* subtle connotation for data types
| other than lists without somehow bringing in an implicit assumption that
| a list is a valid value where you want to convey the idea that something
| is either a string or doesn't exist, or is either a number or doesn't
| exist, or is either a hash table or doesn't exist.

  Why do you want to do this in Common Lisp when you have your perfect
  little toy language Dylan that gets it right?  Is this how you idiots
  think that people will choose Dylan?  Insult the best language on earth,
  take criticism personally, be obnoxiously obtuse and do not get the
  point, then give them Dylan in shining armor as the answer.  Good luck.

| Scheme is way too limiting.  We've got far more in common with CL than
| we have with Scheme.  Scheme isn't even an option any more than Jensen &
| Wirth Pascal is an option.

  Why do you have this desire to have things in common with other people?
  That looks like personal insecurity to me.  Is not Dylan enough for you?
  Do you need to reach out and find people to disagree strongly with just
  to feel you have something in "common" with them that you do not focus
  on?  If you have so much in common with somebody, why spend your time
  carping about differences?

  None of this makes any _sense_.  I believe you are just trolls from a
  community that has no future and then you attack the closest competitor
  you think you can annoy into supporting you.

| Funnily enough I know this.  The point of my making this remark is that
| this is *exactly* the tactic that has been used against myself for some
| time, and is now being used against Andreas in, for example, Alain's
| message.

  You still have not figured out that there is a difference between people
  who made up their mind to be outsiders and those who have not.  Please do.

| Whether particular things are good or bad should be decided on the basis
| of logic, not on the basis of argument from authority.

  What kind of idiot _are_ you?  Geez, do you even _believe_ this crap?
  Good and bad _are_ arguments from authority, you annoying little shit.
  If you think logic helps, consider this: The premises on which you base
  your "logic" eventually turn into arguments from authority, no matter
  where you start.  Why is this?  Good and bad do not exist in nature.
  There is no absolute test for goodness or badness out there that is
  independent of people.  Do you think there is, Bruce Hoult?  Do you think
  if you research long enough, you will find elemental particles of good
  and bad that can form the basis of a logic that all people can agree on?

  Good and bad are the results of people who want to live together.  This
  means they _have_ an authority higher than themselves which they accept.
  It can be some funny deity or it can be the fuzzy "community" or it can
  be a set of law and lots of strange things, but people happen to agree on
  what good and bad should be considered in _reference_ to.  A standard of
  ethics, in the non-technical meaning of "standard" _is_ an authority.
  Those who reject it are considered _bad_guys_ in that community.  We have
  a standard for a language that we accept and those who keep quibbling
  over it and when there is no possible way it could ever stop, because
  there is no possible way to change what they keep carping about for no
  good reason are _bad_guys_ to this community.

| Of course that  becomes difficult when you explicitly reject logic, as
| Erik just did.  I  don't know what that leaves, other than tradition and
| accident.

  I just rejected logic?  I reject logic as the proper means to resolve
  ethical problems.  Does that mean I reject _logic_?  You really _are_
  quite insane.  If someone says I should use classical mechanics to learn
  to drive a car, and I think this is inappropriate even though there are
  many elements of mechanics (including the pun) in driving cars, do I
  reject classical mechanics?  Or do I reject its _application_?

  For someone who thinks logic is so great a univeral problem-solver, you
  sure have a funny way of arriving at _your_ conclusions.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Coby Beck
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <IHaN7.131619$Yb.34694165@typhoon.tampabay.rr.com>
"Bruce Hoult" <·····@hoult.org> wrote in message
································@news.paradise.net.nz...
> In article <···············@shell01.TheWorld.com>, Kent M Pitman
> <······@world.std.com> wrote:
>
> > Bruce Hoult <·····@hoult.org> writes:
> >
> > > In article <··············@gondolin.local.net>, Alain Picard
> > > <·······@optushome.com.au> wrote:
> > >
> > > > So what remains?  It still looks like, to me, that it's a different
> > > > way
> > > > of doing things than you're used to, so you immediately conclude it's
> > > > bad.
> > > >
> > > > One thing you'll learn, if you persevere with CL, is that some of the
> > > > brightest minds ever to touch a keyboard have contributed to its
> > > > design,
> > > > directly or indirectly (i.e. via historical accidents).
> > >
> > > What *you* have missed, is that some of those exact same brightest
> > > minds
> > > to ever touch a keyboard went from Common Lisp to design a new language
> > > and did a few things differently the second time around.
> >
> > It's not obvious how anything Alain has said neglects this.
> >
> > Also, Steele, for example, designed Scheme first and then CL.  Was CL a
> > rejection of Scheme for him?  Was his later work with C++ a rejection of
> > CL?  Was his later work with Java a rejection of C++?
>
> Of course you'd hav to ask him to find out, but I suspect that he's been
> seeking a wider audience for his ideas, as first developed in the
> various "lambda the ultimate ..." papers and no doubt refined since.
>
>
> > Just because people are bad at articulating it doesn't mean they
> > are stupid.
>
> That applies in both directions, though you wouldn't know it to read
> many of the replies to myself and Andreas here.
>
>
> > And saying
> >  (when foo ...)
> > is not the same as saying
> >  (when (not (null foo)) ...)
> > at the intention level.  It carries a subtlely different connotation for
> > some of us.
>
> And Andreas and I have much the same subtly different connotation.  The
> only real difference is that we think that perpetuating the old "the
> list is the fundamental datastructure in Lisps" myth is doing the Lisp
> community (of which we are a part) a disservice.
>
> We want to be able to use the *same* subtle connotation for data types
> other than lists without somehow bringing in an implicit assumption that
> a list is a valid value where you want to convey the idea that something
> is either a string or doesn't exist, or is either a number or doesn't
> exist, or is either a hash table or doesn't exist.
>
>
> > If you really want a language with no ability to pun on types, I
> > really do suggest Scheme.
>
> Scheme is way too limiting.  We've got far more in common with CL than
> we have with Scheme.  Scheme isn't even an option any more than Jensen &
> Wirth Pascal is an option.
>
>
> > If you don't like that, and prefer to interact with people
> > who agree with you that only one point of view is possible, then this is
> > not the language for you.  It will not just frustrate you on this point.
> > It will frustrate you on a whole host of issues where the design style
> > has been of similar character.
>
> False premise, false conclusions.
>
>
> > > Are you saying that you're brighter than Moon?
> >
> > I'll save Alain from having to point out that this kind of remark is
> > not a useful debate tactic.
>
> Funnily enough I know this.  The point of my making this remark is that
> this is *exactly* the tactic that has been used against myself for some
> time, and is now being used against Andreas in, for example, Alain's
> message.
>

To be fair, this usually gets used only after all of the arguments are
presented and there is still no consensus.

> It is an invalid debating tactic and I totally reject implications based
> upon it.
>
> Whether particular things are good or bad should be decided on the basis
> of logic, not on the basis of argument from authority.  Of course that
> becomes difficult when you explicitly reject logic, as Erik just did.  I
> don't know what that leaves, other than tradition and accident.

Logic is important but it really is not the only basis for deciding anything,
even a computer language design.  There is also intuition, consensus of
personal opinions and practicality as well as tradition and accident.  Those
are not all bad things by nature and they are all legitimate circumstances.

And sometimes agreeing to disagree is the only reasonable outcome.

--
Coby
(remove #\space "coby . beck @ opentechgroup . com")
From: Takehiko Abe
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <keke-2811012242250001@solg4.keke.org>
In article <···························@news.paradise.net.nz>, Bruce Hoult <·····@hoult.org> wrote:

> 
> What *you* have missed, is that some of those exact same brightest minds 
> to ever touch a keyboard went from Common Lisp to design a new language 
> and did a few things differently the second time around.

Certainly Dylan was not intended to be a next Common Lisp. Its original
goal was different from CL's. I dug up info-mcl mailing list's archive
and located this:

  From Steve Strassmann
  Date: 1992-06-25
  Subject: RE: MCL Framework & Directions
  [...]

  MCL and Dylan are two very different products, and are expected to fill
  the different needs of two very different communities. [...]
  [...]

  Dylan, however, is not aimed at the Lisp market. It's aimed at the
  current market for static languages. We would definitely consider Dylan
  a failure if it only stole support from the lisp community and had no
  impact on the rest of the world. We think there are compelling reasons
  for a static programmer to seriously consider switching to Dylan, and
  we'll do everything we can to get them to do so!

[Note the last line.]

abe

-- 
<keke at mac com>
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-A4EB39.11300029112001@news.paradise.net.nz>
In article <·····················@solg4.keke.org>, ····@ma.ccom 
(Takehiko Abe) wrote:

> In article <···························@news.paradise.net.nz>, Bruce 
> Hoult <·····@hoult.org> wrote:
> 
> > 
> > What *you* have missed, is that some of those exact same brightest 
> > minds 
> > to ever touch a keyboard went from Common Lisp to design a new language 
> > and did a few things differently the second time around.
> 
> Certainly Dylan was not intended to be a next Common Lisp. Its original
> goal was different from CL's. I dug up info-mcl mailing list's archive
> and located this:
> 
>   From Steve Strassmann
>   Date: 1992-06-25
>   Subject: RE: MCL Framework & Directions
>   [...]
> 
>   MCL and Dylan are two very different products, and are expected to fill
>   the different needs of two very different communities. [...]
>   [...]
> 
>   Dylan, however, is not aimed at the Lisp market. It's aimed at the
>   current market for static languages. We would definitely consider Dylan
>   a failure if it only stole support from the lisp community and had no
>   impact on the rest of the world. We think there are compelling reasons
>   for a static programmer to seriously consider switching to Dylan, and
>   we'll do everything we can to get them to do so!
> 
> [Note the last line.]

That's right, and it has bearing on certain design choices such as 
Generic Functions being "sealed" by default and a lot of langauge 
efficiency being acheived through compiler optomizations that rely on 
sealing and a closed-world assumption.  So Dylan tries pretty hard to be 
as efficient as a static language, while still enabling most of the 
dynamic features of CL when you want them.  And some things that can be 
done in CL on the fly are done in Dylan by changing source code and 
recompiling -- you can't change the class of an exisiting object, for 
example, or add slots to existing objects.

This has no bearing on the question here being discussed, of "nil qua 
false".

-- Bruce
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215955602157647@naggum.net>
* Bruce Hoult
| What *you* have missed, is that some of those exact same brightest minds
| to ever touch a keyboard went from Common Lisp to design a new language
| and did a few things differently the second time around.

  But they designed a new language and set up a new community for it!  They
  did _not_ hang around in the Common Lisp community and whine about it.

| Are you saying that you're brighter than Moon?

  Please think about what you are _actually_ saying.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-57AC8D.11225529112001@news.paradise.net.nz>
In article <················@naggum.net>, Erik Naggum <····@naggum.net> 
wrote:

> * Bruce Hoult
> | What *you* have missed, is that some of those exact same brightest 
> | minds
> | to ever touch a keyboard went from Common Lisp to design a new language
> | and did a few things differently the second time around.
> 
>   But they designed a new language and set up a new community for
>   it!  They did _not_ hang around in the Common Lisp community and
>   whine about it.

Who's whining here?

I'm interested in learning the facts of what the differences are between 
CL and Dylan, and what the reasoning is behind those differences (from 
both sides), and to then make my own judgements about whether anything 
of value has been lost in creating Dylan from CL.

Please note that I'm posting in the generic "Lisp" newsgroup, not a 
specialized one for Common Lisp such as c.l.clos.

 
> | Are you saying that you're brighter than Moon?
> 
>   Please think about what you are _actually_ saying.

What I'm _actually_ saying is that the argument "CL was designed by 
genuises, you're not one, so shut up" is not useful.

-- Bruce
From: Pierre R. Mai
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87snayjy32.fsf@orion.bln.pmsf.de>
Bruce Hoult <·····@hoult.org> writes:

> I'm interested in learning the facts of what the differences are between 
> CL and Dylan, and what the reasoning is behind those differences (from 
> both sides), and to then make my own judgements about whether anything 
> of value has been lost in creating Dylan from CL.

This appears to me to be not an unbiased stance.  You seem to have
made up your mind quite some time ago that nothing "of value" has been
lost, and you are now seeking confirmation on this point.  Since you
will be the arbitrator of what is of value and what isn't, there will
be little surprise about the final outcome, will there?

Furthermore you don't seem to acknowledge the fact that value is
always relative to people.  Things aren't of value in themselves.
They are of value, because they are valued by someone.  People often
don't agree on what they value.

Some people have stated here that they do value that (eq 'NIL '()) in
CL.  You obviously don't value such a thing.  So, lucky you that Dylan
does what you value [leaving aside the question that it isn't the
other way around (for all of us)].  CL provides what I value.  Now
that we are aware of the fact that we value different things, can we
move on?

Ah, but we can't, because you need support for your view that Dylan
didn't leave out anything of value from CL.  Maybe we could get the
current NCITS/J13 to publically declare "Dylan has everything that was
good and great about (Common) Lisp, left out all the crap.
Furthermore it wasn't designed by some steenking Committee, so
therefore we declare the whole Common Lisp standard superceded by
[insert Dylan "standard" here]".

Maybe this would get the world to finally see that Dylan is the way
forward, and everything else is just the delusional ranting of people
who just have the _wrong_ values.

Regs, Pierre.

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-92DC25.13430629112001@news.paradise.net.nz>
In article <··············@orion.bln.pmsf.de>, "Pierre R. Mai" 
<····@acm.org> wrote:

> Bruce Hoult <·····@hoult.org> writes:
> 
> > I'm interested in learning the facts of what the differences are 
> > between CL and Dylan, and what the reasoning is behind those
> > differences (from both sides), and to then make my own judgements
> > about whether anything of value has been lost in creating Dylan
> > from CL.
> 
> This appears to me to be not an unbiased stance.  You seem to have
> made up your mind quite some time ago that nothing "of value" has been
> lost

How could I possibly have already made up my mind about such a thing 
when I am not yet an expert in CL?


> and you are now seeking confirmation on this point.  Since you
> will be the arbitrator of what is of value and what isn't, there will
> be little surprise about the final outcome, will there?

You will therefore no doubt express your "little suprise" when I tell 
you that off the top of my head, at least the following things of value 
(to me) have been lost:

- "collect" clause in the loop macro ("for" macro in Dylan)

- incf/decf.  The Dylan ":=" is equivalent to the CL "setf", but Dylan 
lacks incf/decf in particular and the C'ish modification operators ++, 
--, +=, -=, &=, |= etc in general.  I miss this.

[rest snipped as flowing from an incorrect premise]

-- Bruce
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215996064374500@naggum.net>
* Bruce Hoult
| How could I possibly have already made up my mind about such a thing
| when I am not yet an expert in CL?

  Easy.  Just be a moron.  You do a good job of this so far, toghether with
  that other Dylan lunatic, so it is not particularly unlikely that you
  actually are illogical farts who have come here only to annoy people.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Ian Wild
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3C05F96A.17F8752D@cfmu.eurocontrol.int>
Bruce Hoult wrote:
> 
> - incf/decf.  The Dylan ":=" is equivalent to the CL "setf", but Dylan
> lacks incf/decf in particular and the C'ish modification operators ++,
> --, +=, -=, &=, |= etc in general.  I miss this.


Can you not just macro them in?
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-01F18F.00450130112001@news.paradise.net.nz>
In article <·················@cfmu.eurocontrol.int>, Ian Wild 
<···@cfmu.eurocontrol.int> wrote:

> Bruce Hoult wrote:
> > 
> > - incf/decf.  The Dylan ":=" is equivalent to the CL "setf", but Dylan
> > lacks incf/decf in particular and the C'ish modification operators ++,
> > --, +=, -=, &=, |= etc in general.  I miss this.
> 
> 
> Can you not just macro them in?

incf & decf, yes, easily.  The others can't be done without changing the 
compiler's parser to accept them as infix operators.  Which is a matter 
of minutes to do for any particular compiler, of course, but whether 
anyone else wants it I don't know.

-- Bruce
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215995859622102@naggum.net>
* Bruce Hoult
| Please note that I'm posting in the generic "Lisp" newsgroup, not a 
| specialized one for Common Lisp such as c.l.clos.

  But why are not posting in the specialized comp.lang.dylan?

| > | Are you saying that you're brighter than Moon?
| > 
| >   Please think about what you are _actually_ saying.
| 
| What I'm _actually_ saying is that the argument "CL was designed by 
| genuises, you're not one, so shut up" is not useful.

  Nobody has ever said anything even remotely similar to that, and it is
  offensive to attribute such rampant idiocy to people just because _you_
  have a hard time coming up with intelligent arguments.  That you see the
  world in such terms is something you just have to discuss with someone
  who cares.

  And if that _idiotic_ line of yours was not whining, nothing is.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Alain Picard
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <86pu61vqvw.fsf@gondolin.local.net>
Bruce Hoult <·····@hoult.org> writes:

> 
> What *you* have missed, is that some of those exact same brightest minds 
> to ever touch a keyboard went from Common Lisp to design a new language 
> and did a few things differently the second time around.
> 
> Are you saying that you're brighter than Moon?
> 

I tell you what.  You go re-read my post, my _entire_ post,
and try to _understand_ what I _actually_ wrote.

If you're smart enough to 
  1) realize that I didn't insult anyone
  2) realize that YOU just insulted ME
  3) apologize to me for your honest mistake (see, I'm giving
     you the benefit of the doubt here)

THEN I'll consider that it may be worth my while to reply to
you in the future.  This one is a freebie.  :-)

Have a nice day.

-- 
Against stupidity, the Gods themselves contend in vain.
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-198DC2.00544930112001@news.paradise.net.nz>
In article <··············@gondolin.local.net>, Alain Picard 
<·······@optushome.com.au> wrote:

> Bruce Hoult <·····@hoult.org> writes:
> 
> > 
> > What *you* have missed, is that some of those exact same brightest 
> > minds 
> > to ever touch a keyboard went from Common Lisp to design a new language 
> > and did a few things differently the second time around.
> > 
> > Are you saying that you're brighter than Moon?
> > 
> 
> I tell you what.  You go re-read my post, my _entire_ post,
> and try to _understand_ what I _actually_ wrote.
> 
> If you're smart enough to 
>   1) realize that I didn't insult anyone

No, you insulted Andreas by effectively accusing him of acting in bad 
faith.


>   2) realize that YOU just insulted ME

Did that *really* need a "smiley"?  I'm sorry.  I should probably not 
reply to other people in the same session in which I have to deal with 
Erik.


>   3) apologize to me for your honest mistake (see, I'm giving
>      you the benefit of the doubt here)

No offense to you was intended.

 
> THEN I'll consider that it may be worth my while to reply to
> you in the future.

THAT is entirely up to you.

-- Bruce
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3216064927754484@naggum.net>
* Bruce Hoult
| I should probably not reply to other people in the same session in which
| I have to deal with Erik.

  You imply that you are _personally_ affected by my articles.  _This_ is
  your core problem.  _This_ is how these things develop badly.  Quit it!
  Become a _professional_, and just _quit_ the stupid personal reactions.
  It is the sheer stupidity of your _professional_ opinion as posted to a
  professional forum that is attacked here.  You do _not_ have a personal
  opinion on nil vs false, or on language design.  (If you have, keep it
  yourself.)  When you post professional bullshit, you should _expect_ to
  be treated harshly.  If you do not understand this, suppose you are in a
  meeting where the object to design something, and you bring up your
  idiocy again and again and refuse to get the point.  Do you think people
  will tolerate you?  If you persist in being an idiot in a professional
  setting, you _will_ be beaten up and thrown out of the forum.  Do you
  think anyone will care how _you_ feel, when you have ignored the whole
  reason for the forum's existence?  People have a _purpose_ when they come
  to a forum like this.  The fundamental premise is that you are here to
  share information and knowledge and professional opinions in order to
  further a clearly constructive interest.  When you violate that premise,
  you are what is known on USENET as a troll.  Much less favorable terms
  are applied in real life to people who violate the premises for a forum.

  You have a moral obligation to be intelligent when you post to a forum
  for professional discussions, which you have not understood and do not
  appreciate.  If you take these things personally, you are making a very
  serious mistake.  Yet, if you are unprofessional, there is something
  wrong with _your_ attitude, not just your arguments and opinions, and
  _you_ need to fix it.  Since you are in a professional forum, critique of
  your (personal) behavior is _not_ about _you_, it is about your _role_ in
  this forum.  If you do not understand this, you will miss most of what is
  going on, here.  If you are taking things so personally that you lose
  your mental balance, you should spend time with someone who cares about
  you, even if paid to do so, and talk it out.  Newsgroups are not therapy
  sessions.

  The above quoted line was obviously intended on your part to blame me for
  your mental instability, because you think this is a forum where anyone
  cares how you feel and why.  It is not.  (People may care, but that is a
  personal choice, not the purpose of the newsgroup.)  It is increasingly
  evident that you Dylan guys are here to get personal affirmation of your
  misguided _professional_ choices, which is highly inappropriate for a
  professional forum.  If you have that kind of personal needs, imposing
  them on other people is the pinnacle of inconsiderateness and rudeness,
  but people who think their personal feelings should be on CNN every day,
  do use USENET for this.  Now, sharing personal stories is one thing, but
  demanding that other people satisfy one's personal needs is just plain
  bad behavior.  Those who think they have a "right" to push their personal
  concerns on other people never consider any other person or concerns, and
  hence do not tolerate that anybody else reprimand them for their behavior
  because those others do not have the "right" to do so in their view.
  This whole "rights" thing is very strange, and basically just nonsense.
  It is as if someone has been watching too many crime-fighting TV shows
  and think that anyone who criticizes them for anything has to follow the
  strict rules of a government agency and violate their "rights" if not.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215520010240664@naggum.net>
* Bruce Hoult
| That's right, except that you can't in CL distinguish between the empty 
| list and false.

  Geez, could you quit carping about this and start _listening_ some day
  soon?  That distinction is made in the protocol described in the
  documentation of the function you are using.  It is never a problem
  because Common Lisp programmers do not _want_ to use false and the empty
  list at the same time any more than C programmers want to put null bytes
  in their strings or put any objects at the very beginning of memory.

  It is the Sapir-Whorff hypothesis all over again.  Because the language
  does not do it, its (smarter) programmers do not want to do it.  You want
  to do something like this because you have yet to internalize the rules
  of the language.  The more you think it is "wrong", the less likely you
  are to grasp what the rules of the language _are_.

| That's a pretty much completely useless argument.

  Yeah, I figured you would not get it.  I think you are a waste of time
  this time, too.  You are one of those guys who make up their mind what
  the world should be like, and then blame the world for not conforming.
  It is _not_ Common Lisp's fault you do not like some of its features.
  There is consequently nothing that _Common_Lisp_ can do to fix this.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87pu64gstl.fsf@teonanacatl.andreas.org>
Erik Naggum <····@naggum.net> writes:

>   It is _not_ Common Lisp's fault you do not like some of its features.
>   There is consequently nothing that _Common_Lisp_ can do to fix this.

Yes, but Lisp can fix it.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Wade Humeniuk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <9u0blf$s8v$1@news3.cadvision.com>
> >   It is _not_ Common Lisp's fault you do not like some of its features.
> >   There is consequently nothing that _Common_Lisp_ can do to fix this.
>
> Yes, but Lisp can fix it.
>

It is not broken.  It is a feature not a mistake.  If some people are not
happy with CL then they can write a new Lisp in CL (as a new shadowed
package, or would people rather write it in C?).  Nothing is stopping them,
create a language that has false.

Wade
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87zo58f7ep.fsf@teonanacatl.andreas.org>
"Wade Humeniuk" <········@cadvision.com> writes:

> > Yes, but Lisp can fix it.
> It is not broken. 

People's opinion about this one varies, as well as about other
features.  The argument "It's not broken because CL says so" doesn't
count.  I'm interested in arguments that sound like "CL does the Right
Thing because..." or "CL does the Wrong Thing because...".

I'm sure you can think of CL features that bother you enough that you
would change them if given the chance, but not enough to keep you from
using CL.

> It is a feature not a mistake. 

This sounds like a Microsoft argument.  There are such things as
misfeatures.

> If some people are not
> happy with CL then they can write a new Lisp in CL (as a new shadowed

Now this sounds like the typical argument of defenders of C: "I can
show you that my language is Turing-complete, so I can solve any
problem you can."

I can write my new Lisp in itself, as it is expected from any serious
language.

> package, or would people rather write it in C?).  Nothing is stopping them,
> create a language that has false.

Been there, done that, trying to share the experience.  Well,
actually, I just help maintaining the Gwydion Dylan system, and was
neither involved in the design of the language nor it's
implementation, people smarter than me from the Lisp community have.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215920795532553@naggum.net>
* Andreas Bogk
| People's opinion about this one varies, as well as about other features.
| The argument "It's not broken because CL says so" doesn't count.

  "It is not illegal just because the law says so", said the criminal, ...

| I'm interested in arguments that sound like "CL does the Right
| Thing because..." or "CL does the Wrong Thing because...".

  ... "I am only interested in arguments that sound like <whatever>".

  I think we have ourselves another specimen of that immature humanoid who
  has yet to figure out that _people_ actually count.

  Let me be nasty for a second.  How old are you, Andreas?  18?  16?

  That people can agree to things without proof of excellence is a good
  thing.  But I guess Dylan is just as anal-retentive as Scheme and that
  the reason we have a current influx of Dylanites is that nothing happens
  in the Dylan community.

  The biggest problem with all these "logical" types is that they have no
  clue how to choose the premises from which they draw their conclusions,
  they just take them for granted, unquestioned, received by revelation,
  and cannot fathom that anyone would disagree with their premises, only
  with their conclusions.  E.g., the premise that technical debates in a
  community who has already agreed on a large standard are based in logic
  from _their_ choice of technical premises.  That is simply _wrong_.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Tim Bradshaw
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <fbc0f5d1.0111260507.6fee1bcc@posting.google.com>
Kent M Pitman <······@world.std.com> wrote in message news:<···············@shell01.TheWorld.com>...

> And what about programs that return type (or foo bar).  Is
> there a type (NULL-OF (OR FOO BAR)) that is distinct from type (NULL-OF FOO)
> and type (NULL-OF BAR)?  If so, it sounds like a mess to represent and 
> recognize.  But ok, maybe.  I didn't think this through utterly but I feel
> the phrase "set of all sets not contained in any set" is going to enter this
> discussion really soon now...  I do know that every time there has been a
> serious discussion of solving this, such a bubble really does creep in.  
> No matter what set someone is returning, there's always a desire to squeeze
> in just one extra element ... and often it defeats the whole point of having
> picked the size of data storage one has chosen.  

I think it's at least some exponential blowup thing.  If you have n
basic types, then I think you have 2^n possible types like (or ...),
and you want each of these to have a distinct NULL-OF, so you need 2^n
distinct values.
And we have satisfies as a type descriptor too (oops, lots and *lots*
of NULL-OFs now), and what about (null-of (or foo (member (null-of
foo)))), or even better (null-of (not (member (null-of foo))))?

--tim
From: ·······@Yahoo.COm
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <ffdf35bb.0112102026.36ed4d32@posting.google.com>
Kent M Pitman <······@world.std.com> wrote in message news:<···············@shell01.TheWorld.com>...
> ... or look at the
> opposite outcome in the utterly stupid Base64 MIME encoding, which requires
> 65(!) characters to correctly represent it, so never really compacts up
> quite right.

Long ago, mid-late 1970's, I figured out a solution to this, long before
MIME ever was invented, to wit a reasonable syntax for strings that
doesn't need special escape characters within the string nor one extra
character outside the character-space to delimit strings. (Anybody
remember MRPP3 also known as POX on SU-AI = sail.stanford.edu ? This
was to be in the next MRPPn incarnation but I never got around to it.)
It works like this: You have two sets of pairs of nesting characters:
Assymtric ones like () [] {} <>
Symmetric ones like "" '' !! ||
A string segment is an open nesting character followed by any sequence
of characters not containing either opening or closing nesting character
followed by close nesting character. For example [foo!!(((baz] is a
string segment that has eleven characters. A string is any number of
string segments side by side with nothing intervening. So if you want
to include a whole bunch of characters which happened to include EVERY
one of the possible nesting characters, you merely need to break it up
into segments such that each segment consistently avoids whatever nesting
characters are used around it. For example, here's one possible way to
write the list of nesting pair with spaces between them:
"() [] {} <>"[ "" '' !! ||]
PRINT would of course try to minimize the number of segments with which
to express any given string, preferring to use a single segment bounded
by "" whenever none of the internal characters is " just as it does in CL now.
Note that this way of expressing strings avoids both the MIME problem
of needing an extra character that itself cannot be included inside
a string, and the Common LISP problem where any string that has lots
of " marks within it is very ugly, such as "\"\"\"\"\"\"\"\"\"\"" which
prints to more than twice the length of the actual string, as you see.
CL has a similar problem with names of symbols that contain special
characters, which could have been handled by an almost identical syntax.

Note, I would reserve () for lists, but probably use most/all the other
nesting pairs to delimit string segments. (In LISP you can't use ''
because ' already is a prefix read-macro for (quote ...), but in my
proposed super-POX that wouldn't have been a problem.) So why couldn't
MIME have come up with something like that?? (For that matter, why didn't
CL come up with something like that either??)
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwadxe8bo0.fsf@shell01.TheWorld.com>
"Pierre R. Mai" <····@acm.org> writes:

> Bruce Hoult <·····@hoult.org> writes:
...
> > type.  How often do C programs fail because some function gets passed a 
> > null pointer that didn't expect it?
> 
> This is a direct contradiction to your previous statement.  Either
> every datatype deserves its own "don't know" or "doesn't exist" value,
> which a null pointer in C arguably is, because it _can't_ clash with
> any valid pointer value, or we forbid "don't know" values, because we
> fear that receivers might not anticipate them and fail to handle them
> correctly.

Yes, indeed.  A *huge* number of Java programming errors that I've seen
people have great difficulty tracking down are due to the failure of
people to have to use a separated null type.  In effect, every type is
secretly (or null the-type-i-thought-i-was-getting) and the syntax encourages
people to not remember the null, so they are continually baffled by the fact
that such a "typesafe"(R) language has lied to them.  I had forgotten 
about this horrifyingly common syndrome at the office where I found myself
watching this play out day after day after day, but that is certainly enough
all by itself to make me think I'm glad we don't have null objects PER SE
for all of our types.  That doesn't mean at all that I mind having empty
lists or empty strings when they are properly degenerate cases of a more
general class and all the operators work on them in the expected way.
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwk7wc5cpe.fsf@shell01.TheWorld.com>
Erik Naggum <····@naggum.net> writes:

> * Erik Naggum
> > Get over your personal hangup and just accept the language for what it
> > is.  _Nothing_ will _ever_ happen to the language just because you keep
> > having these problems.  Nobody is interested in your lack of will to
> > accept the language while you are learning it.
> 
> * Andreas Bogk
> | Can anybody explain to me why some people regard the Common Lisp standard
> | as gospel?
> 
>   Well, why do you regard it as gospel?  Why do _you_ think in such terms?
>   Explain this, and you will be much closer to the wisdom you seek.
> 
> | What happened to the spirit of continuous improvement that has led Lisp
> | through the decades?
> 
>   The keyword here is "continuous". [...]

I'll put the same thought another way.  I'd say the keyword was
"improvement".

CL provides a base from which to move *forward*.  Re-analyzing the base is
not moving forward but *laterally*.

No one denies that there can be hill-climbing problems in any field, 
requiring some backup before moving forward.  But the cost of backing out
of assumptions is generally higher than the cost of not doing so, so to 
not be causing people gratuitous extra cost, one would want to justify the
need to back up.

Of course, not everyone ever moved forward to use all of what ANSI CL
has in the first place.  Such people don't feel the cost of backing up
in the same way as people who did.  That leads to people talking at
crossed purposes about what the "big deal" is.  To those who have an
investment in a certain way of doing things, it is a major big deal
and the cost is not just "belief" (those who are not invested probably
think it's all a matter of "saving face" or "people being stuck in
their thoughts" as if reading a new paper could change them out of it)
but "action" (this translates quickly to "dollars" in translation,
quality assurance, etc. and steals precious budget form "finishing
product", "marketing", "new features", etc.).

So to Andreas my question back would be...

"Can anybody explain to me why some people regard musical standards as
a good use of anyone's time?"  Even just discussing it seems unproductive.

I don't mean discussing technical flaws--that makes sense.  But discussing
the conceptual gestalt and trying to get community consensus that "the
standard should be deviated from" seems pointless.  People have the ability
to answer this question each individually for themselves; no group consensus
is required.  And one reason it's important to have a standard is that 
standards are convergent.  Those of adhering have a community of common
knowledge to share.  Not adhering is divergent; non-adherents don't always
have something to share since they may diverge in different ways.  In that
sense, a discussion of Python or Dylan as a specific alternative is better
than a mere bitch session on why people don't like what they have.
From: Andreas Bogk
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87itbwf0yf.fsf@teonanacatl.andreas.org>
Kent M Pitman <······@world.std.com> writes:

> CL provides a base from which to move *forward*.  Re-analyzing the base is
> not moving forward but *laterally*.

I'd dispute that. Re-analyzing the the Axiom of Parallels in geometry
resulted in the development of non-Euclidean geometry, which was a
tremendous success.

> No one denies that there can be hill-climbing problems in any field, 
> requiring some backup before moving forward.  But the cost of backing out
> of assumptions is generally higher than the cost of not doing so, so to 
> not be causing people gratuitous extra cost, one would want to justify the
> need to back up.

An obvious process.  One must not forget to account the savings
reached against the costs, and the possibility of reducing the cost by
analyzing it's nature.

> crossed purposes about what the "big deal" is.  To those who have an
> investment in a certain way of doing things, it is a major big deal
> and the cost is not just "belief" (those who are not invested probably
> think it's all a matter of "saving face" or "people being stuck in
> their thoughts" as if reading a new paper could change them out of it)
> but "action" (this translates quickly to "dollars" in translation,
> quality assurance, etc. and steals precious budget form "finishing
> product", "marketing", "new features", etc.).

I think I want to understand what these issues are.

> "Can anybody explain to me why some people regard musical standards as
> a good use of anyone's time?"  Even just discussing it seems unproductive.

Musicians who only play by the standards might be technically
excellent, but boring.  Interesting music is the one violating the
standards in a way that doesn't sound unpleasant to the listener
regardless.  Bad music violates the standards and sounds bad.

> I don't mean discussing technical flaws--that makes sense.  But discussing
> the conceptual gestalt and trying to get community consensus that "the
> standard should be deviated from" seems pointless.  People have the ability

No. It's called progress. Even if such a discussion process doesn't
actually result in a change of consensus, it is still vital for
teaching the deeper ideas.

Not doing that leads to loss of adaptibility, which could become a
problem when prerequisits change.

> have something to share since they may diverge in different ways.  In that
> sense, a discussion of Python or Dylan as a specific alternative is better
> than a mere bitch session on why people don't like what they have.

But it doesn't answer the question what choices to make given the
chance of starting from scratch.

Andreas

-- 
"In my eyes it is never a crime to steal knowledge. It is a good
theft. The pirate of knowledge is a good pirate."
                                                       (Michel Serres)
From: Erik Naggum
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3215921991944430@naggum.net>
* Andreas Bogk
| I'd dispute that. Re-analyzing the the Axiom of Parallels in geometry
| resulted in the development of non-Euclidean geometry, which was a
| tremendous success.

  Did anything happen to Euclidean geometry because of this re-evaluation?

  Or did the development of non-Euclidean geometries prove useful in ways
  that did not impact the remainder of Euclid's The Elements _at_all_?  Was
  it not one of the amazingly interesting features of non-Euclidean
  geometry that it did _not_ contradict or have a stupid quarrel with the
  rest of his work?

  So why are you still here when you should be in comp.lang.dylan extolling
  the features of non-<whatever> Lisps?  Who do you think cares?  Invite
  Lisp people to your own very low-traffic forum to discuss this with you,
  rather than annoy people with your repetitive nonsense, OK?  Or are you,
  as I now strongly suspect, only posting in comp.lang.lisp because you
  think Lisp people should be "converted" to Dylan because nobody else are?

  By the way, what you call "axiom" is called "postulate" in Euclid because
  of the distinction that Aristotle drew between the two concepts.  But I
  suppose you do not recognize Euclid's The Elements as authoritative on
  what Euclid said, either.  "It is so because Euclid said so" seems to be
  an invalid argument to you, but I am afraid that I have no "logical"
  answer that I expect will sate your desire for pathological nonsense.

///
-- 
  The past is not more important than the future, despite what your culture
  has taught you.  Your future observations, conclusions, and beliefs are
  more important to you than those in your past ever will be.  The world is
  changing so fast the balance between the past and the future has shifted.
From: Coby Beck
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <b4aN7.131476$Yb.34660418@typhoon.tampabay.rr.com>
"Erik Naggum" <····@naggum.net> wrote in message
·····················@naggum.net...
> * Andreas Bogk
> | I'd dispute that. Re-analyzing the the Axiom of Parallels in geometry
> | resulted in the development of non-Euclidean geometry, which was a
> | tremendous success.
>
>   Did anything happen to Euclidean geometry because of this re-evaluation?
>
>   Or did the development of non-Euclidean geometries prove useful in ways
>   that did not impact the remainder of Euclid's The Elements _at_all_?  Was
>   it not one of the amazingly interesting features of non-Euclidean
>   geometry that it did _not_ contradict or have a stupid quarrel with the
>   rest of his work?
>
>   So why are you still here when you should be in comp.lang.dylan extolling
>   the features of non-<whatever> Lisps?  Who do you think cares?  Invite
>   Lisp people to your own very low-traffic forum to discuss this with you,
>   rather than annoy people with your repetitive nonsense, OK?  Or are you,
>   as I now strongly suspect, only posting in comp.lang.lisp because you
>   think Lisp people should be "converted" to Dylan because nobody else are?
>

FWIW I find these cross language disscussions for the most part educational.
Perhaps it is just because I am not as familiar with all the arguments and
criticisms as Erik is and he is obviously fed up with it.

That said, I have not yet seen anything brought up that makes me less satisfied
with the solutions common lisp provides.  I looked over Paul Grahams Arc page
and while I find all of the goals he expresses fine, the examples he has so far
of things he wants different from CL strike me as very trivial and very
personal.  The points raised so far in this thread about #f vs nil and '() etc
are interesting and I believe support the idea that there is another approach.
But Common Lisp has not taken that approach and I see no problem as it is.  If
things were broken enough that you had to start from scratch, these are
interesting issues, but with such a fine and established base as we have now,
these are moot points.

Common Lisp doesn't have if*; in Common Lisp nil == '() == false; Common Lisp
has too many parens in its cond form; Common Lisp has a loop macro that is very
un-lispy......so what?  *Nothing* there is even _remotely_ unuseable or
unsupportable.  And the flexibility is built in to the language to to modify so
much to your own personal tastes.  All the energy spent trying to sugar coat
lisp for the masses would be so much better spent developing all those huge
libraries Java and Perl people miss so much.

I do not beleive popularity is a bad thing and I would honestly like to see
lisp grow its user base.  But it is not worth _any_ sacrifice in the integrity
of its design.  Jan Derzen said something along the lines of "if they have to
be converted, who wants them".  While I can't agree with that as stated, I do
feel that if you show someone the light and they don't see it, that is there
problem.  Too many parens is *not* what keeps people from appreciating lisp.

--
Coby
(remove #\space "coby . beck @ opentechgroup . com")
From: Tim Bradshaw
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <fbc0f5d1.0111290441.65f3abf0@posting.google.com>
"Coby Beck" <·····@mercury.bc.ca> wrote in message news:<························@typhoon.tampabay.rr.com>...
> 
> I do not beleive popularity is a bad thing and I would honestly like to see
> lisp grow its user base.  But it is not worth _any_ sacrifice in the integrity
> of its design.  Jan Derzen said something along the lines of "if they have to
> be converted, who wants them".  While I can't agree with that as stated, I do
> feel that if you show someone the light and they don't see it, that is there
> problem.  Too many parens is *not* what keeps people from appreciating lisp.

And since we're here there are some other quite popular languages that
have NIL/false-equivalent equations.  Like, erm, C and C++ (0 is
false), Python (which makes all sorts of things false like ""), and
Perl (similar rules to Python maybe, certainly "" and 0, and
disturbingly enough also "0").

--tim
From: Thomas F. Burdick
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <xcvn115fhqi.fsf@conquest.OCF.Berkeley.EDU>
··········@tfeb.org (Tim Bradshaw) writes:

> And since we're here there are some other quite popular languages that
> have NIL/false-equivalent equations.  Like, erm, C and C++ (0 is
> false), Python (which makes all sorts of things false like ""), and
> Perl (similar rules to Python maybe, certainly "" and 0, and
> disturbingly enough also "0").

Yeah, well just wait for Perl 12, when they'll make "naught" false :-P

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Daniel Barlow
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <87snaxwucl.fsf@noetbook.telent.net>
··········@tfeb.org (Tim Bradshaw) writes:

> Perl (similar rules to Python maybe, certainly "" and 0, and
> disturbingly enough also "0").

Also ``undef'' - but note _not_ "0e0"

The hazier reaches of my memory tell me that this "zero-but-true"
value has actually been used for that purpose in some Perl module.
Don't remember what, though.  Could have been DBI-related or something
to do with Oraperl.

OK, so this is offtopic for the group (seems mostly ontopic for the
thread, though).  I'm procrastinating about putting together this
month's FTX13; I wouldn't even be reading this otherwise.


-dan

-- 

  http://ww.telent.net/cliki/ - Link farm for free CL-on-Unix resources 
From: Brian Palmer
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <0whlmgp8kbx.fsf@elaine0.Stanford.EDU>
Daniel Barlow <···@telent.net> writes:

> ··········@tfeb.org (Tim Bradshaw) writes:
> 
> > Perl (similar rules to Python maybe, certainly "" and 0, and
> > disturbingly enough also "0").
> 
> Also ``undef'' - but note _not_ "0e0"
> 
> The hazier reaches of my memory tell me that this "zero-but-true"
> value has actually been used for that purpose in some Perl module.
> Don't remember what, though.  Could have been DBI-related or something
> to do with Oraperl.

Even more fun, the value "0 but true" evaluates to 0 in numeric
contexts, but is considered true in boolean expressions. Plus it's a
little clearer what's going on than "0e0".

-- 
Brian Palmer
"Whoever fights monsters should see to it that in the process he does
not become a monster. And when you look long into an abyss, the abyss
also looks into you"  - Nietzsche
From: Bruce Hoult
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <bruce-5EC3C4.10242930112001@news.paradise.net.nz>
In article <····························@posting.google.com>, 
··········@tfeb.org (Tim Bradshaw) wrote:

> And since we're here there are some other quite popular languages that
> have NIL/false-equivalent equations.  Like, erm, C and C++ (0 is
> false), Python (which makes all sorts of things false like ""), and
> Perl (similar rules to Python maybe, certainly "" and 0, and
> disturbingly enough also "0").

I am heartened to see that you find that disturbing.  The risks in Perl 
of real data looking like "false" are immense.  I know, because I write 
a lot of Perl.  Most of it is supposed to be "throw away", but we all 
know what happens to throw-away code ... it comes back to bite your bum 
a couple of decades later.

-- Bruce
From: ·······@Yahoo.Com
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <ffdf399b.0112101516.6c8f91c7@posting.google.com>
···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) wrote in message news:<···············@conquest.OCF.Berkeley.EDU>...
> ...  I
> *really* just wanted to refute the idea that it was nuts to separate
> NIL and false.

Actually on first glance it's nuts to separate 0 and false.
For efficiency, we have INUMs whereby the number 0 is represented
by an actual machine value of 0, 1 by a machine value of 1, etc.
up to the machine maximum positive value in a register, and likewise
-1 is represented by machine -1, etc. down to the most-negative machine
value in a register. So small-integer arithmetic can be done simply
as machine arithmetic with check for overflow after each single
operation, no conversion to/from LISP representation except when the
result exceeds the machine contents-of-register range.
For similar efficiency reasons, false is represented by machine zero
in most programming languages. That way a test for false (and skip
or jump according to the result is a single instruction that references
only a single machine register before deciding what to do. By comparison,
if false is not a machine zero, then testing for false requires comparing
two different registers to see if they are identical, the register of
interest and some register allocated to hold the false value all the
time. (In LISP, the false value is the internal representation of a
pointer to the symbol called NIL in the COMMON-LISP package.) On many
CPUs, this requires two instructions, one to compare the two registers
and set flags, and a second to actually skip or jump depending on the flags,
and it ties up a register, and requires referencing that register too.
So on first glance false should be machine-zero which we already are
using for LISP-zero-number, so () and false and 0 should all be the same
LISP object, namely machine zero. So why make up a totally new symbol
NIL for the false value and for the empty list the way LISP does??

Strawman: Well, functions that return indices into sequences like to
return 0 if the result is the very first index and false if nothing
was found.

Rebuttal: Those very special class of functions can use a different
convention for nothing-found without stepping on everyone else's toes.
They can return -1 to indicate the index of nothing found. Or they can
use 1-origin indexing like most other languages. Everyone else can
use 0 to represent false or empty list, and programmers can be warned
of this special class of functions that use -1 instead of 0 for failure
result, just as we're already warned that FIRST means NTH 0 instead
of NTH 1 etc. Restrict the weirdness to just those very few functions
that can't deal with the usual rule of 0 = () = false, instead of
making all machine code in the whole language run slower by having
false not the same as machine 0.

Strawman: But then 0 would be a special case of an object that is both
a number and a list.

Rebuttal: But NIL is a special case of an object that is both a symbol
and a list, and furthermore it is not in the keyword package yet you
aren't allowed to change its value to be anything other than itself.
Furthermore T is also a special case, where you aren't allowed
to change its value even though it's not in the keyword package.
If 0 were the standard false and emptylist object, and 1 were the
standard true value, both would be constants because they are really
numbers rather than as special cases. It's actually a royal pain that
in mathematical software I can't set T to be a number the way I
can set X Y Z W U V and S to be numbers. Also with 0=false and 1=true
it would be just like Boolean algebra instead of another way to re-invent
the wheel with NIL and T.

Furthermore, if 0 instead of NIL were the emptylist and false value,
a list of empty lists would print as far fewer characters (0 0 0 0 0)
and be much easier to visually inspect for non-false elements, compared
to (NIL NIL NIL NIL MIL NIL NIL NIL) which has one non-false element
but can you spot it instantly?? And a list of boolean values would
print uniformly as for example (0 1 1 0 1 0) instead of (NIL T T NIL T NIL)
making it a lot easier to format them for display in tabular form.

Furthermore, NIL, a contraction of Latin nihil, isn't even a common
word in English much less a word at all in some other languages,
whereas 0 is recognized as zero in all modern Western languages
and even orientals recognize the Western zero digit even if they don't
like to use it outside computer systems.

Summary: There's nothing wrong with a single value representing both
false and the empty list or empty set, with all other values being
treated as "true" for most purposes, but having that single falise value
be the contraction-of-Latin NIL instead of the number 0 seems absurd,
and having that false and empty value NOT be machine zero is dopey too.
It's too late to change it, but it's something slightly unreasonable
we just gotta accept when learning LISP rather than something that is
basically reasonble and we actually like. NIL is like CAR and CDR, sigh.
(L and R would be better names for left and right side of dotted pair,
given that LISP is written in English anyway??)
(Yeah, I know the IBM 7090 history, sigh.)
(Bad idea: For non-English speakers, M and N would be easier to remember
than CAR and CDR or L and R. So instead of CADDAR we'd have MNNM.)
From: Coby Beck
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <MzbR7.38498$oj3.8367502@typhoon.tampabay.rr.com>
<·······@Yahoo.Com> wrote in message
·································@posting.google.com...
> ···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) wrote in message
news:<···············@conquest.OCF.Berkeley.EDU>...
> > ...  I
> > *really* just wanted to refute the idea that it was nuts to separate
> > NIL and false.
>
> Actually on first glance it's nuts to separate 0 and false.

good thing a second glance is possible!

--
Coby
(remove #\space "coby . beck @ opentechgroup . com")
From: Ian Wild
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <3C15C5CF.98DFA872@eurocontrol.int>
·······@Yahoo.Com wrote:
> 
> For similar efficiency reasons, false is represented by machine zero
> in most programming languages.

This is simply not true. *Most* programming languages are
quite concerned with providing a layer of abstraction between
the programmer and the raw bit patterns.
From: Kent M Pitman
Subject: Re: On nil qua false [was: Re: On conditionals]
Date: 
Message-ID: <sfwlmg9khp8.fsf@shell01.TheWorld.com>
·······@Yahoo.Com writes:

> ···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) wrote in message news:<···············@conquest.OCF.Berkeley.EDU>...
> > ...  I
> > *really* just wanted to refute the idea that it was nuts to separate
> > NIL and false.
> 
> Actually on first glance it's nuts to separate 0 and false.

Absent compatibility and tradition constraints, I'm pretty sure it 
would work fine to use 0 as the false value.  

> It's too late to change it, but it's something slightly unreasonable
> we just gotta accept when learning LISP rather than something that is
> basically reasonble and we actually like. NIL is like CAR and CDR, sigh.

More or less I agree with this.

> (L and R would be better names for left and right side of dotted pair,
> given that LISP is written in English anyway??)

Indeed.  People often wanted to replace CAR/CDR with FIRST/REST but it
never quite takes because people like CADR, etc.  I've sometimes
suggested that LHS and RHS would compose better.  (LRHS, for example,
could replace CADR. Of course, I'm about 10,000 times better at
telling car from cdr than I am at telling left from right.  Even as I
wrote this example I wrote RLHS, not out of a transcription error but
because I was misremembering that Right is not the, er, leftmost
element. Sigh.  Some human errors die hard.  So something else more
critical might be lost if we moved to Right/Left distinctions...  or
maybe I'd finally in my old age learn to tell right from left because
the distinction would become important enough to matter.  Even when
driving, which I seem to reliably do right, having someone point
rather than say "turn right", helps a lot more...)  But beyond all
that, CAR/CDR do have a lot of tradition there, and violating that
tradition has a cost.
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215377267841910@naggum.net>
* Thomas F. Burdick
| Would it really kill people to put a couple (not (null ..))s here and
| there, and make their intentions more explicit?

  Yes.  Adding (not (null ...)) to previously obvious code would make
  everything nearly unreadable.  Besides, the intention _is_ to return the
  empty list to those who look for a list and false to those who want a
  boolean value.  This is an important property of Common Lisp.  Scheme
  does not have this property, and consequently Scheme systems have a
  gazillion small functions that are anal-retentively type-specific.  One
  of the reasons I like Common Lisp is that it has none of this nonsense.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Kent M Pitman
Subject: Re: On conditionals
Date: 
Message-ID: <sfw3d37k9s1.fsf@shell01.TheWorld.com>
Kenny Tilton <·······@nyc.rr.com> writes:

> "Thomas F. Burdick" wrote:
> >  I don't even see any good reason why NIL should
> > be false. 

As to the choice of the symbol, I somewhat agree.  It's tradition, but
one I could have done without.  On the other hand, in my 20+ year
career doing some fairly intensive Lisp, I've found it a minor
irritation once or twice, but basically have never found it got in the
way in any seriously material way ... so I guess I just don't buy any
argument that it matters.

As to the choice of the empty list being false, I also don't see a problem
there and actually see some virtue.  I think all too much fuss has been
made over this.

> Understood, but in this case the proof is in the pudding for me. By
> which I mean, programming with nil as false is so terrific it must be
> Deeply Right.

In the MOO programming language, which (I think by design) has a very
Lispy feel, a bunch of objects are false, including 0 and "" and {}.
Errors are also false.  They make the mistake of making their type OBJ
(sort of vaguely like our standard class) be false, and that causes
problems.  But the other values being false don't cause any problem to
learn and it's quite handy to have these various degenerate cases all
count as false.  MOO is a byte compiled language and not overly
obsessed with efficiency; there's probably something good about being
able to do a truth test in one instruction, so maybe it's not awful
that we have a single false value.  But even so, I think that, if
anything, we lose out by not having more false values, not by failing
to jump on the Scheme bandwagon of "everything is bad but the
explicit".

> isn't there a funny essay somewhere about the consequences of porting
> something from Lisp to Scheme, specifically about the problem of having
> to then differentiate between nil and false? I recall assoc figuring
> prominently in the piece.

Well, people often do (cdr (assoc ...)) in LISP, and it's true that assoc
returns false when it fails, which you can't cdr.  But you also can't cdr
the empty list in Scheme.  So it would be a problem anyway.
From: Christophe Rhodes
Subject: Re: On conditionals
Date: 
Message-ID: <sq3d3712ib.fsf@cam.ac.uk>
Kent M Pitman <······@world.std.com> writes:

> Kenny Tilton <·······@nyc.rr.com> writes:
> 
> > "Thomas F. Burdick" wrote:
> > >  I don't even see any good reason why NIL should
> > > be false. 
> 
> As to the choice of the symbol, I somewhat agree.  It's tradition, but
> one I could have done without.  On the other hand, in my 20+ year
> career doing some fairly intensive Lisp, I've found it a minor
> irritation once or twice, but basically have never found it got in the
> way in any seriously material way ... so I guess I just don't buy any
> argument that it matters.

It's not a serious material way, but it has caused irritation to me
that I can't use T as a variable.  It's easily-get-roundable, of
course...

[(defun d2x/dt2 (x xdot y ydot time)
   ...)]

... but it has still once or twice gotten me to say "Aaargh" :-)

Cheers,

Christophe
-- 
Jesus College, Cambridge, CB5 8BL                           +44 1223 510 299
http://www-jcsu.jesus.cam.ac.uk/~csr21/                  (defun pling-dollar 
(str schar arg) (first (last +))) (make-dispatch-macro-character #\! t)
(set-dispatch-macro-character #\! #\$ #'pling-dollar)
From: Lieven Marchand
Subject: Re: On conditionals
Date: 
Message-ID: <m3adxepuzs.fsf@localhost.localdomain>
Kenny Tilton <·······@nyc.rr.com> writes:

> isn't there a funny essay somewhere about the consequences of porting
> something from Lisp to Scheme, specifically about the problem of having
> to then differentiate between nil and false? I recall assoc figuring
> prominently in the piece.

http://www.lisp.org/humor/large-programs.html

-- 
Lieven Marchand <···@wyrd.be>
She says, "Honey, you're a Bastard of great proportion."
He says, "Darling, I plead guilty to that sin."
Cowboy Junkies -- A few simple words
From: Nicolas Neuss
Subject: Re: On conditionals
Date: 
Message-ID: <wspu66yebi.fsf@ortler.iwr.uni-heidelberg.de>
During an earlier thread on the NIL/false issue, Kent Pitman pointed
to a website with a very interesting discussion of this issue (if I
remember correctly, it was within the ANSI committee).  Unfortunately,
I can't find that link anymore.  Could someone help me?

Thank you, Nicolas.

P.S.: Sorry, if it was mentioned already in this thread.  I couldn't
bear reading this never-ending story in whole length again...
From: Kent M Pitman
Subject: Re: On conditionals
Date: 
Message-ID: <sfwk7we2113.fsf@shell01.TheWorld.com>
Nicolas Neuss <·····@ortler.iwr.uni-heidelberg.de> writes:

> During an earlier thread on the NIL/false issue, Kent Pitman pointed
> to a website with a very interesting discussion of this issue (if I
> remember correctly, it was within the ANSI committee).  Unfortunately,
> I can't find that link anymore.  Could someone help me?
> 
> Thank you, Nicolas.
> 
> P.S.: Sorry, if it was mentioned already in this thread.  I couldn't
> bear reading this never-ending story in whole length again...

The ANSI group didn't have a web site, so this isn't enough
information to jog my memory.  Maybe someone else will remember
another clue.
From: Nicolas Neuss
Subject: Re: On conditionals
Date: 
Message-ID: <wswv0dhmx7.fsf@ortler.iwr.uni-heidelberg.de>
Kent M Pitman <······@world.std.com> writes:

> Nicolas Neuss <·····@ortler.iwr.uni-heidelberg.de> writes:
> 
> > During an earlier thread on the NIL/false issue, Kent Pitman pointed
> > to a website with a very interesting discussion of this issue (if I
> > remember correctly, it was within the ANSI committee).  Unfortunately,
> > I can't find that link anymore.  Could someone help me?
> > 
> > Thank you, Nicolas.
> > 
> > P.S.: Sorry, if it was mentioned already in this thread.  I couldn't
> > bear reading this never-ending story in whole length again...
> 
> The ANSI group didn't have a web site, so this isn't enough
> information to jog my memory.  Maybe someone else will remember
> another clue.

I'm sorry, I messed this up.  The reference I had in mind was about
another "hot" topic, namely the single namespace vs. double namespace
issue.  Of course, when adjusting my memory, I found the reference
immediately.  It is your report (together with Gabriel)

 http://world.std.com/~pitman/Papers/Technical-Issues.html

A pity, that there is nothing similar for the nil/false issue.

Anyway, I'm sorry for my confusion.

Yours, Nicolas.
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215376680290370@naggum.net>
* Thomas F. Burdick
| I'm not so sure about false, though.  I don't like the pun that () is the
| same as boolean false.  I also don't like that the empty list is a
| symbol.  Don't get me wrong, it's easy enough to cope with, but it's
| conceptually sloppy.

  I find it conceptually very clean.  I find it equally conceptually clean
  that 0 is false in C.  Neither do I have any problems with Perl's false
  values.  I do have a problem with Scheme's anal-retentive false, because
  it is so goddamn hard to obtain a false.

| I don't even see any good reason why NIL should be false.

  There has to be at least one false value.  Making the empty list false is
  simply a very good choice for a language that gives you lists as a close
  to primitive type.  Linked lists have to be terminated by _something_,
  and that something might as well be the answer to the question: "Are
  there any more elements?" as a matter of pragmatics.

| So, I guess what I'm saying is that you ought to explain your objection
| here (or point to a message where you've explained it before, since I'm
| sure you have).

  I have lost track of which objection you might be referring to here, but
  I hazard a guess it is that I think making nil different from false is
  nuts.  It is nuts from a pragmatic point of view.  Conceptualizations
  that go against the pragmatic are even more wrong than Scheme in general,
  but it is precisely because Scheme's conceptulization is impractical that
  they have chosen to make their language impractical but conceptually
  pure.  I think Scheme is an excellent example of how you go wrong when
  you decide that "practicality" is a worthless axis to find a reasonable
  position on, or not even consider at all.  Common Lisp is a practical
  language and its conceptualization is one of trying to figure out what
  the most elegant practical expression would be, not how impractical the
  most elegant expression would be.  This is just something Scheme freaks
  will never accept as a point of serious difference between Common Lisp
  and Scheme.  I look at Scheme from a Common Lisp viewpoint, of course,
  and that is not very productive, but Dorai Sitaram brought up this Scheme
  nonsense as a reasonable way to talk about Common Lisp features.  I think
  I put it sufficiently clear when I started my reply with "Scheme is all
  wrong".  Those who do not think so are of course free to talk about
  Scheme all they want, but the sheer _insistency_ that Scheme freaks come
  to present their "views" about Common Lisp is really annoying.  At least
  they have their own community, so it is not as if they are fragmenting
  the _Common_ Lisp community, but they also think they have a Lisp, and
  that is at least as annoying.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Thomas F. Burdick
Subject: Re: On conditionals
Date: 
Message-ID: <xcvg077lkaw.fsf@apocalypse.OCF.Berkeley.EDU>
Erik Naggum <····@naggum.net> writes:

> * Thomas F. Burdick
> | I'm not so sure about false, though.  I don't like the pun that () is the
> | same as boolean false.  I also don't like that the empty list is a
> | symbol.  Don't get me wrong, it's easy enough to cope with, but it's
> | conceptually sloppy.
> 
>   I find it conceptually very clean.  I find it equally conceptually clean
>   that 0 is false in C.  Neither do I have any problems with Perl's false
>   values.  I do have a problem with Scheme's anal-retentive false, because
>   it is so goddamn hard to obtain a false.

Bleah, I guess this is just a matter of taste, then.  I personally
think that false should have a type of boolean, not integer nor
symbol.  And, honestly, I don't see anything about #F as different
from () and NIL that would make it hard to get, per se.  When I'm
testing for the end of a list, I write (cond ((null foo) ...)).  When
I'm testing for not-the-end, I write (cond ((not (null foo)) ...>))
rather than (cond (foo ...)), because I want to be explicit about my
intentions.  But I guess that shows that there's a lot of style issues
mixed in here.

[ As for Perl, you really don't mind the *string* "0" being false?!?! ]

> | I don't even see any good reason why NIL should be false.
> 
>   There has to be at least one false value.  Making the empty list false is
>   simply a very good choice for a language that gives you lists as a close
>   to primitive type.  Linked lists have to be terminated by _something_,
>   and that something might as well be the answer to the question: "Are
>   there any more elements?" as a matter of pragmatics.

Actually, I meant NIL qua symbol, not the empty list.  Although, if I
had my druthers, () wouldn't be false either.  I just don't see what's
so hard about writing (not (null ...)).

> | So, I guess what I'm saying is that you ought to explain your objection
> | here (or point to a message where you've explained it before, since I'm
> | sure you have).
> 
>   I have lost track of which objection you might be referring to here, but
>   I hazard a guess it is that I think making nil different from false is
>   nuts.

That would be it.

>   It is nuts from a pragmatic point of view.  Conceptualizations
>   that go against the pragmatic are even more wrong than Scheme in
>   general, but it is precisely because Scheme's conceptulization is
>   impractical that they have chosen to make their language
>   impractical but conceptually pure.

While I won't argue with that characterization of Scheme, I don't
think that seperating () and false is choosing purity over
practicality.  I think it's easier to read code that checks for NIL
explicitly, and I don't think that checking with the NULL predicate is
a particular hinderance.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215379161045820@naggum.net>
* Thomas F. Burdick
| Bleah, I guess this is just a matter of taste, then.

  Nonono, you are just _wrong_.  :)

| And, honestly, I don't see anything about #F as different from () and NIL
| that would make it hard to get, per se.

  It would mean that functions need to know whether they should return an
  empty list or a boolean.  This is the reason that the pun is useful, just
  as 0 being false in C is useful.  I actually find s specific boolean type
  to be incredibly painful -- to use it, you would always need multiple
  values.  It is not unlike asking real people "Do you know the time?".
  "Yes" is not a good answer.  Just the time will do nicely, thank you.  If
  you had me test for, say, find returning true before I could use its
  return value, I would probably write macros to circumvent such nonsense.

| [ As for Perl, you really don't mind the *string* "0" being false?!?! ]

  That Perl does type conversions east and west so you never actually know
  what type of object you are dealing with is sometimes convenient par
  excellence, but most of the time, it is just plain nuts.  However, it is
  actually useful in a number of languages.  SQL, for instance, gets around
  some of its syntax problems with this flexibility.

| Actually, I meant NIL qua symbol, not the empty list.  Although, if I had
| my druthers, () wouldn't be false either.  I just don't see what's so
| hard about writing (not (null ...)).

  Well, it looks like really bad language design.  Like Scheme.  Failing to
  have a function that turns something into a boolean directly is bad.  If
  you want to see if foo is a non-empty list, (not (null foo)) looks dumb,
  but if you are expecting a list, (consp foo) is the right choice, in
  which case you are well advised to look at typecase instead of cond.

| While I won't argue with that characterization of Scheme, I don't think
| that seperating () and false is choosing purity over practicality.

  Well, conflating "nothing" and "false" has long traditions in both logic
  and programming languages.  I think objection to it come only from a
  misguided sense of purity without a sense of history or continuity.

| I think it's easier to read code that checks for NIL explicitly, and I
| don't think that checking with the NULL predicate is a particular
| hinderance.

  Well, if you used typecase and tested for null and cons and other types,
  I would probably support you, but (not (null ...)) says "Scheme freak!"
  to me, and in a horrible font, too.  :)

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Thomas F. Burdick
Subject: Re: On conditionals
Date: 
Message-ID: <xcv7ksjpjai.fsf@conquest.OCF.Berkeley.EDU>
Erik Naggum <····@naggum.net> writes:

>   Well, if you used typecase and tested for null and cons and other types,
>   I would probably support you, but (not (null ...)) says "Scheme freak!"
>   to me, and in a horrible font, too.  :)

Well, it's not something I do often -- I'm actualy very prone to using
etypecase.  I just grepped through several hundred lines of code (and
a Lisp compiler, no less, so it makes unusually heavy use of lists),
and found about .6 instances per hundred lines of "(not (null ", which
is about what I expected.  The vast majority of the time, consp or
typecase is the right thing to do, and it looks like I usually use
(not (null ...)) when I'm expecting the value to be nil.  As in:

  (defun foo (list bar)
    (if (not (null list))
        (do-something #'foo list bar)
        (let ((qux ...))
          (do-the-rest-of-the-function))))

Maybe other people's coding style involves cases where this test would
come up more often?  I don't know.  Or, maybe it's because I learned
Scheme first.  Ah, well, surviving habits from scheme, maybe, but not
freakiness.

-- 
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                               
   |     ) |                               
  (`-.  '--.)                              
   `. )----'                               
From: Dmitri Ivanov
Subject: Re: On conditionals
Date: 
Message-ID: <9tid20$1smn$1@news.aha.ru>
Erik Naggum <····@naggum.net> wrote in message
·····················@naggum.net...
>   Well, conflating "nothing" and "false" has long traditions in both
logic
>   and programming languages.  I think objection to it come only from a
>   misguided sense of purity without a sense of history or continuity.

Someone may need to go beyond Boolean logic. Any three-valued or
multi-valued logic implementer would prefer to interpret NIL as
undefined or something else different form false.

Everyone who deals with database programming knows that AND, OR, and
other logical connectives has three-valued interpretation in SQL. I
consider this quite natural. Several lisp modules for relational
database access (SQL/ODBC and the like) makes database's NULL be
converted into/from Lisp's NIL. In this use, NIL would be considered as
an undefined value rather than the false value.
--
Sincerely,
Dmitri Ivanov
www.aha.ru/~divanov
From: Janis Dzerins
Subject: Re: On conditionals
Date: 
Message-ID: <873d37kq96.fsf@asaka.latnet.lv>
···@apocalypse.OCF.Berkeley.EDU (Thomas F. Burdick) writes:

> When I'm
> testing for the end of a list, I write (cond ((null foo) ...)).

Have you considered using function endp?

-- 
Janis Dzerins

  Eat shit -- billions of flies can't be wrong.
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215357851897754@naggum.net>
* Espen Vestre
| the perl "expression if" does not work that way:

  Perl is not a language worth comparing anything to.

| (perl's _unless_, which can't be mentioned often enough since some people
|  think lisp is the only language with such an animal, can of course also
|  be used as a "expression unless").

  Just being postfix does not make it an expression.

* Erik Naggum
> One question is whether a form should be used for its value or not.  The
> forms when and unless should clearly not be used for their value. 

* Espen Vestre
| I strongly disagree. I think when and unless can be perfectly well used
| for their value. In general I think the Common Lisp programmer should be
| free to use any form for it's value whenever that value can be given a
| meaningful interpretation.

  Well, unlike what a Perl hacker will expect,

(setq foo (when bar zot))

  actually does modify foo when bar is false.  I think using the one-branch
  conditionals when and unless for value is highly, highly misleading.

  However, if they are used in a function body as the value-returning form
  and it is defined to return nil when "nothing happens", I think it is
  much more perspicuous to have an explicit (return nil) form under the
  appropriate conditions than let when or unless fall through and return
  nil by default, which can be quite invisible.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Joe Schaefer
Subject: Re: On conditionals
Date: 
Message-ID: <m3k7wj997o.fsf@mumonkan.sunstarsys.com>
Erik Naggum <····@naggum.net> writes:

>   Well, unlike what a Perl hacker will expect,
> 
> (setq foo (when bar zot))
> 
>   actually does modify foo when bar is false.  

Huh?  That's exactly what a perl hacker would expect; in fact, s/he'd 
also expect foo = zot whenever bar is true, and foo = bar otherwise.  
*That* might be surprising to a lisp programmer, though :)

<ot>
Both conditionals and loop constructs usually have return values 
in Perl; the conditional itself is returned whenever there is no 
successful alternative.  Perl's for/foreach are the exceptions here, 
not the rule.
</ot>

-- 
Joe Schaefer
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215365347672515@naggum.net>
* Erik Naggum
>   Well, unlike what a Perl hacker will expect,
> 
> (setq foo (when bar zot))
> 
>   actually does modify foo when bar is false.  

* Joe Schaefer
| Huh?  That's exactly what a perl hacker would expect; in fact, s/he'd
| also expect foo = zot whenever bar is true, and foo = bar otherwise.
| *That* might be surprising to a lisp programmer, though :)

  Heh, not at all, because if bar is false, foo will equal bar in Common
  Lisp, too, although it is a slightly unusual way to look at it.  Since
  there is but one false value in Common Lisp, and Perl has a whole range
  of them, I suppose there is Perlish sense in your version of this.

  What I had in mind, however, was that Espen Vestre's example using a
  postfix if would cause the statement preceding it _not_ to be evaluated
  if the condition was false.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Joe Schaefer
Subject: Re: On conditionals
Date: 
Message-ID: <m3elmr8wik.fsf@mumonkan.sunstarsys.com>
Erik Naggum <····@naggum.net> writes:

> * Erik Naggum
> >   Well, unlike what a Perl hacker will expect,
> > 
> > (setq foo (when bar zot))
> > 
> >   actually does modify foo when bar is false.  
> 
> * Joe Schaefer
> | Huh?  That's exactly what a perl hacker would expect; in fact, s/he'd
> | also expect foo = zot whenever bar is true, and foo = bar otherwise.
> | *That* might be surprising to a lisp programmer, though :)
> 
>   Heh, not at all, because if bar is false, foo will equal bar in Common
>   Lisp, too, although it is a slightly unusual way to look at it.  Since
>   there is but one false value in Common Lisp, and Perl has a whole range
>   of them, I suppose there is Perlish sense in your version of this.

Of course you're right; but I probably should point out that this 
also applies to negated conditionals and loops as well (where the 
returned conditional is something true):

  % perl -wle '$a="cond"; sub f { unless ($a) {"cons"} }; print f'
  cond
  % perl -wle 'sub f { ($a="cond", "cons") until $a }; print f'
  cond

>   What I had in mind, however, was that Espen Vestre's example using a
>   postfix if would cause the statement preceding it _not_ to be
>   evaluated if the condition was false.

I know what you meant- I've just never seen anyone attempt
to write a "postfix if" in lisp before :).  Now if you could 
tell me whether or not a postfixed conditional declaration is 
"legal" Perl ...

(please don't answer that- it's a rhetorical question :)

-- 
Joe Schaefer
From: Erik Naggum
Subject: Re: On conditionals
Date: 
Message-ID: <3215382980307036@naggum.net>
* Joe Schaefer <··········@sunstarsys.com>
| (please don't answer that- it's a rhetorical question :)

  Whew!  You had me nervous there for a second.

///
-- 
  Norway is now run by a priest from the fundamentalist Christian People's
  Party, the fifth largest party representing one eighth of the electorate.
-- 
  Carrying a Swiss Army pocket knife in Oslo, Norway, is a criminal offense.
From: Alain Picard
Subject: Re: On conditionals
Date: 
Message-ID: <86itc3chmy.fsf@gondolin.local.net>
Espen Vestre <·····@*do-not-spam-me*.vestre.net> writes:

> I strongly disagree. I think when and unless can be perfectly well used
> for their value. In general I think the Common Lisp programmer should
> be free to use any form for it's value whenever that value can be given
> a meaningful interpretation.

Well, Erik was talking about _style_.  I know I couldn't keep my
lunch down if I saw something like

(setf foo (when (valid? bar) (blah)))  ; Using implicit NIL as valid return

But I'd have no problems with

(setf foo (if (valid? bar)
              (blah)
              nil))

I only use WHEN and UNLESS in things like

(unless (valid? bar)
   (error 'invalid-bar-error))


To each his own, I guess...

-- 
It would be difficult to construe        Larry Wall, in  article
this as a feature.			 <·····················@netlabs.com>
From: Takehiko Abe
Subject: Re: On conditionals
Date: 
Message-ID: <keke-2211011845080001@solg4.keke.org>
In article <··············@gondolin.local.net>, Alain Picard <·······@optushome.com.au> wrote:

> Espen Vestre <·····@*do-not-spam-me*.vestre.net> writes:
> 
> > I strongly disagree. I think when and unless can be perfectly well used
> > for their value. In general I think the Common Lisp programmer should
> > be free to use any form for it's value whenever that value can be given
> > a meaningful interpretation.
> 
> Well, Erik was talking about _style_.  I know I couldn't keep my
> lunch down if I saw something like
> 
> (setf foo (when (valid? bar) (blah)))  ; Using implicit NIL as valid return

Why? You immediately know what it does when you see "(when ".

I sometimes write
  (let ((foo (when bar ....)))
      ...

instead of (if bar (progn ....) nil)

> 
> But I'd have no problems with
> 
> (setf foo (if (valid? bar)
>               (blah)
>               nil))

With IF, my eyes look for else form [only to find NIL at the end
in this case.] That's slightly more work.

abe

-- 
<keke at mac com>
From: Pierre R. Mai
Subject: Re: On conditionals
Date: 
Message-ID: <878zczeyfm.fsf@orion.bln.pmsf.de>
····@ma.ccom (Takehiko Abe) writes:

> In article <··············@gondolin.local.net>, Alain Picard <·······@optushome.com.au> wrote:
> 
> > Espen Vestre <·····@*do-not-spam-me*.vestre.net> writes:
> > 
> > > I strongly disagree. I think when and unless can be perfectly well used
> > > for their value. In general I think the Common Lisp programmer should
> > > be free to use any form for it's value whenever that value can be given
> > > a meaningful interpretation.
> > 
> > Well, Erik was talking about _style_.  I know I couldn't keep my
> > lunch down if I saw something like
> > 
> > (setf foo (when (valid? bar) (blah)))  ; Using implicit NIL as valid return
> 
> Why? You immediately know what it does when you see "(when ".
> 
> I sometimes write
>   (let ((foo (when bar ....)))
>       ...
> 
> instead of (if bar (progn ....) nil)

You could use (and bar ....) instead.  That would make the value more
explicit to my eyes.  But it's not something I worry about, I can read
the when form just fine, I'd just probably write the and version
myself.

Regs, Pierre.

-- 
Pierre R. Mai <····@acm.org>                    http://www.pmsf.de/pmai/
 The most likely way for the world to be destroyed, most experts agree,
 is by accident. That's where we come in; we're computer professionals.
 We cause accidents.                           -- Nathaniel Borenstein
From: Takehiko Abe
Subject: Re: On conditionals
Date: 
Message-ID: <keke-2211012350200001@solg4.keke.org>
In article <··············@orion.bln.pmsf.de>, "Pierre R. Mai" <····@acm.org> wrote:

> > Why? You immediately know what it does when you see "(when ".
> > 
> > I sometimes write
> >   (let ((foo (when bar ....)))
> >       ...
> > 
> > instead of (if bar (progn ....) nil)
> 
> You could use (and bar ....) instead.  That would make the value more
> explicit to my eyes. 

Yes. I agree. I do use (and bar ...) too. I realized that I've been
inconsistent in this.

Thanks,
abe

-- 
<keke at mac com>
From: Tim Bradshaw
Subject: Re: On conditionals
Date: 
Message-ID: <fbc0f5d1.0111220439.68638be5@posting.google.com>
I'm not really following up here (I think I agree with Erik's article
insofar as it needs agreement, and it was certainly interesting).  I
was prompted by some earlier discussion on this stuff to look at what
I tend to write - I don't have `style rules' but then I'm writing code
in a team of one so I don't have to formalise things fortunately.  But
I definitely do have some informal rules on IF, WHEN, UNLESS which are
quite similar to those here (I don't think I use WHEN/UNLESS for
value).

But anyway, what was more interesting was to look at what I did with
NOT and NULL and conditionals.  I have never thought about this until
I read through code, and I still don't understand why I write what I
do.  For instance why this:

(when (not x) ...)

instead of

(unless x ...)

-- I use both, and they have different meanings to me (not to CL). 
Not to mention (NOT (NULL ...)):

(when (not (null x)) ...)
(unless (null x) ...)

-- I have both these too, why?  They have different connotations to
me, but I'm not sure why.  Sometimes I can look back through CVS logs
and catch myself changing one into the other.  And back again.

--tim