From: neo88
Subject: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <6a73bb68.0408221716.25fdc66c@posting.google.com>
Hi all,

I found this a while ago (before I got into Lisp):
http://rikkus.info/ten_commandments.html
Entitled "The Ten Commandments for C++ Programmers"

I thought it would be fun if some of the programmers here wrote up
their top ten. Newer programmers would be welcome to as well. If I get
a good enough response, I may post them somewhere on the web. Here is
my number 1:
 
1) Thou shalt use the Machine to accomplish those chores that are
tedious and full of longetivity with the Macro.

I haven't really thought of any other good ones. Let me know what you
think. BTW, this can be humorus too, we programmers don't have to be
serious all the time. :-P

-- 
May the Source be with you.
neo88 (Philip Haddad)

From: Pascal Bourguignon
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <87acwm3aml.fsf@thalassa.informatimago.com>
······@truevine.net (neo88) writes:
> I found this a while ago (before I got into Lisp):
> http://rikkus.info/ten_commandments.html
> Entitled "The Ten Commandments for C++ Programmers"

It could be entitled "The Ten Commandments for OO Programmers". They
could apply almost verbatim to CLOS programmers...


-- 
__Pascal Bourguignon__                     http://www.informatimago.com/

Our enemies are innovative and resourceful, and so are we. They never
stop thinking about new ways to harm our country and our people, and
neither do we.
From: neo88
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <6a73bb68.0408230920.1da4562b@posting.google.com>
Pascal Bourguignon <····@thalassa.informatimago.com> wrote in message news:<··············@thalassa.informatimago.com>...
> ······@truevine.net (neo88) writes:
> > I found this a while ago (before I got into Lisp):
> > http://rikkus.info/ten_commandments.html
> > Entitled "The Ten Commandments for C++ Programmers"
> 
> It could be entitled "The Ten Commandments for OO Programmers". They
> could apply almost verbatim to CLOS programmers...

I didn't mean just OO. I meant Lisp in general. BTW, you can't have
class destructors and virtual classes in CLOS can you? I have only
been working with CLOS for about two weeks....

-- 
May the Source be with you.
neo88 (Philip Haddad)
From: Coby Beck
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <SysWc.48836$X12.27631@edtnps84>
"neo88" <······@truevine.net> wrote in message
·································@posting.google.com...
> Pascal Bourguignon <····@thalassa.informatimago.com> wrote in message
news:<··············@thalassa.informatimago.com>...
> > ······@truevine.net (neo88) writes:
> > > I found this a while ago (before I got into Lisp):
> > > http://rikkus.info/ten_commandments.html
> > > Entitled "The Ten Commandments for C++ Programmers"
> >
> > It could be entitled "The Ten Commandments for OO Programmers". They
> > could apply almost verbatim to CLOS programmers...
>
> I didn't mean just OO. I meant Lisp in general. BTW, you can't have
> class destructors and virtual classes in CLOS can you? I have only
> been working with CLOS for about two weeks....

Look up initialize-instance and shared-initialize and allocate-instance in
the Hyper Spec for some related tools.

-- 
Coby Beck
(remove #\Space "coby 101 @ big pond . com")
From: Thomas A. Russ
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <ymiu0urcclv.fsf@sevak.isi.edu>
······@truevine.net (neo88) writes:

For the most part, you don't need either of the following in CLOS, since
they are in C++ to address issues (problems?) in that language which are
handled differently in CLOS.

> I didn't mean just OO. I meant Lisp in general. BTW, you can't have
> class destructors 

Since Lisp has automatic storage management, you don't (usually) need to
have destructors to release memory for you.  It is handled automatically
for all objects that are part of the main Lisp language.

There are some extensions to provide GC finalizers so that things like
resources (typically OS resources) from outside Lisp can be released
when objects are about to be garbage collected.  This is not
standardized, however.

> and virtual classes in CLOS can you? 

With the caveat about my limited knowledge of C++, I think that all CLOS
classes would be considered virtual in C++.  That is why there isn't any
problem with setting up multiple-path inheritance networks using CLOS
classes.  Since CLOS "does this right" :), you don't need to take any
special actions when using multiple inheritance.

>I have only
> been working with CLOS for about two weeks....

So, what do you think about it?
Do you like the different paradigm for OO programming?

-- 
Thomas A. Russ,  USC/Information Sciences Institute
From: ·········@random-state.net
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <cgcj06$6jshn$1@midnight.cs.hut.fi>
Pascal Bourguignon <····@thalassa.informatimago.com> wrote:

> It could be entitled "The Ten Commandments for OO Programmers". They
> could apply almost verbatim to CLOS programmers...

I don't agree. Here's point-by-point:

 "1.  Thou shalt not rely solely on the compiler-generated default
  methods for construction, destruction, copy construction, or assignment
  for any but the simplest of classes. Thou shalt scrupulously forge these
  "foremost four" methods for any non-trivial class, yea, even though thy
  implementation be but trivial. Further, thou shalt declare and define
  thy destructor as virtual such that others may become heir to the fruits
  of your labors with ease."

I see no relation to CLOS here. If you need simple accessors, etc. the
generated ones will be fine. Likewise, unless you need methods on
SHARED-INTIALIZE or frieds, there is no sense in defining them.

 "2. Thou shalt not violate the "is-a" rule by abusing the inheritance
  mechanism for thine own twisted perversions. Denounce with vigor the
  primordial OO publications wherein this sinful behavior was epitomized."

OK, this one probably does apply. Convoluted class hierarchies are
convoluted class hierarchies. On the other hand, dynamic mixin based
behaviours work quite well in CLOS, but I'm not sure if that is referred
to here.

 "3. Thou shalt not rely on any implementation-dependent behavior of a
  compiler, operating system, nor hardware environment, lest your code be
  forever caged within that dungeon whilst others code scampers unfettered
  through architectures as yet undreamt ···@

Make that "...any undefined behaviour..." and it applies. Relying on
features and extensions present in your environment is fine IMO -- though
awareness of the general presence of equivalent features is a good thing.

 "4. Thou shalt not augment the interface of a class at the
  "concrete" level without most prudent deliberation. Such ill-begotten
  practices imprison thy clients unjustly into your classes, and foment
  unspeakable unrest when code maintenance and extension are required.

I'm not sure what this means at all. Maybe because my C++ skills are very
very weak.

 "5. Thou shalt restrict thy friendship to truly worthy
  contemporaries. Beware, for thou art exposing thyself wellnigh as rudely
  as from a trench coat."

Not applicable: slots are available for those who really want them. We're
not as shy and close-minded as the C++ folks; if your clients reach for
the zipper^Wslot-value they know what they're getting into.

 "6. Thou shalt not abuse your implementation data by making it public or
  static except in the rarest of circumstances. Thy bits are thine
  own; share them not with others."

Ditto. Well, almost anyways: don't export accessors that are not part of
the interface, but that's it IMO.

 "7. Thou shalt not suffer dangling pointers or references to be harbored
  within your objects. These are nefarious and precarious agents of random
  and wanton destruction. While ye may escape their wrath, thy fellow
  programmer may verily be ravaged by them."

Bwhahaaa. ;) "Here's a nickel, go and buy yourself a garbage collector."

 "8. Thou shalt make use of available class libraries as conscientiously
  as possible. Code reuse, not just thine own but that of your clients as
  well, is the holy grail of OO. A seemly set of class libraries will put
  you on a path where you may be enlightened."

Well, we're not so hot on holy (I hope), but using existing libraries and
built-in facilities is certainly a good thing -- so this one does apply.

 "9. Thou shalt forever forswear the use of the vile printf/scanf, rather
  favoring the flowing streams. Cast off thy vile C cloak and partake of
  the wondrous fruit of flexible and extensible IO."

Well. Not applicable.

 "10. Thou shalt avoid designing "big" classes--classes with both an
  unseemly abundance of instance data and tortuosly complicated
  interfaces. Such accursed classes are the unclean and unwieldy result of
  poor design. Be chastened, seek truth, and design again, that thy userid
  may be enshrined among the enumeration of the most purely virtuous."

Amen. 

 (In case you wonder about the morality of full inclusion of the original
  here, I'm as pure as the keeper of http://rikkus.info/ who says "I
  dont know who wrote this. If you do, please tell me so I can give
  credit.".)

Cheers,

 -- Nikodemus                   "Not as clumsy or random as a C++ or Java. 
                             An elegant weapon for a more civilized time."
From: Reini Urban
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <4129eb9c$1@e-post.inode.at>
·········@random-state.net schrieb:
> Pascal Bourguignon <····@thalassa.informatimago.com> wrote:
>>It could be entitled "The Ten Commandments for OO Programmers". They
>>could apply almost verbatim to CLOS programmers...

These commandments are almost impossible to understand for non-native 
english speakers. Maybe it would be a fine goal to write them down in 
modern english. Substance over style please.

Amen.

> I don't agree. Here's point-by-point:
> 
>  "1.  Thou shalt not rely solely on the compiler-generated default
>   methods for construction, destruction, copy construction, or assignment
>   for any but the simplest of classes. Thou shalt scrupulously forge these
>   "foremost four" methods for any non-trivial class, yea, even though thy
>   implementation be but trivial. Further, thou shalt declare and define
>   thy destructor as virtual such that others may become heir to the fruits
>   of your labors with ease."
> 
> I see no relation to CLOS here. If you need simple accessors, etc. the
> generated ones will be fine. Likewise, unless you need methods on
> SHARED-INTIALIZE or frieds, there is no sense in defining them.
> 
>  "2. Thou shalt not violate the "is-a" rule by abusing the inheritance
>   mechanism for thine own twisted perversions. Denounce with vigor the
>   primordial OO publications wherein this sinful behavior was epitomized."
> 
> OK, this one probably does apply. Convoluted class hierarchies are
> convoluted class hierarchies. On the other hand, dynamic mixin based
> behaviours work quite well in CLOS, but I'm not sure if that is referred
> to here.
> 
>  "3. Thou shalt not rely on any implementation-dependent behavior of a
>   compiler, operating system, nor hardware environment, lest your code be
>   forever caged within that dungeon whilst others code scampers unfettered
>   through architectures as yet undreamt ···@
> 
> Make that "...any undefined behaviour..." and it applies. Relying on
> features and extensions present in your environment is fine IMO -- though
> awareness of the general presence of equivalent features is a good thing.
> 
>  "4. Thou shalt not augment the interface of a class at the
>   "concrete" level without most prudent deliberation. Such ill-begotten
>   practices imprison thy clients unjustly into your classes, and foment
>   unspeakable unrest when code maintenance and extension are required.
> 
> I'm not sure what this means at all. Maybe because my C++ skills are very
> very weak.
> 
>  "5. Thou shalt restrict thy friendship to truly worthy
>   contemporaries. Beware, for thou art exposing thyself wellnigh as rudely
>   as from a trench coat."
> 
> Not applicable: slots are available for those who really want them. We're
> not as shy and close-minded as the C++ folks; if your clients reach for
> the zipper^Wslot-value they know what they're getting into.
> 
>  "6. Thou shalt not abuse your implementation data by making it public or
>   static except in the rarest of circumstances. Thy bits are thine
>   own; share them not with others."
> 
> Ditto. Well, almost anyways: don't export accessors that are not part of
> the interface, but that's it IMO.
> 
>  "7. Thou shalt not suffer dangling pointers or references to be harbored
>   within your objects. These are nefarious and precarious agents of random
>   and wanton destruction. While ye may escape their wrath, thy fellow
>   programmer may verily be ravaged by them."
> 
> Bwhahaaa. ;) "Here's a nickel, go and buy yourself a garbage collector."
> 
>  "8. Thou shalt make use of available class libraries as conscientiously
>   as possible. Code reuse, not just thine own but that of your clients as
>   well, is the holy grail of OO. A seemly set of class libraries will put
>   you on a path where you may be enlightened."
> 
> Well, we're not so hot on holy (I hope), but using existing libraries and
> built-in facilities is certainly a good thing -- so this one does apply.
> 
>  "9. Thou shalt forever forswear the use of the vile printf/scanf, rather
>   favoring the flowing streams. Cast off thy vile C cloak and partake of
>   the wondrous fruit of flexible and extensible IO."
> 
> Well. Not applicable.
> 
>  "10. Thou shalt avoid designing "big" classes--classes with both an
>   unseemly abundance of instance data and tortuosly complicated
>   interfaces. Such accursed classes are the unclean and unwieldy result of
>   poor design. Be chastened, seek truth, and design again, that thy userid
>   may be enshrined among the enumeration of the most purely virtuous."
> 
> Amen. 
> 
>  (In case you wonder about the morality of full inclusion of the original
>   here, I'm as pure as the keeper of http://rikkus.info/ who says "I
>   dont know who wrote this. If you do, please tell me so I can give
>   credit.".)
-- 
Reini Urban
http://xarch.tu-graz.ac.at/home/rurban/
From: Joost Kremers
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <slrncijrn2.d4.joostkremers@j.kremers4.news.arnhem.chello.nl>
Reini Urban wrote:
> ·········@random-state.net schrieb:
>> Pascal Bourguignon <····@thalassa.informatimago.com> wrote:
>>>It could be entitled "The Ten Commandments for OO Programmers". They
>>>could apply almost verbatim to CLOS programmers...
>
> These commandments are almost impossible to understand for non-native 
> english speakers. Maybe it would be a fine goal to write them down in 
> modern english. Substance over style please.

replace thou and thee with you, thy/thine with your, and shalt with
shall. all the other words should be in a dictionary.
(<http://www.webster.com>, <http://dictionary.cambridge.org> may help.)

> Amen.

amen to you too, brother. ;-)

-- 
Joost Kremers                                      ············@yahoo.com
Selbst in die Unterwelt dringt durch Spalten Licht
EN:SiS(9)
From: Hannah Schroeter
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <cgvnbh$r7s$1@c3po.use.schlund.de>
Hello!

Reini Urban  <······@x-ray.at> wrote:
>·········@random-state.net schrieb:
>> Pascal Bourguignon <····@thalassa.informatimago.com> wrote:
>>>It could be entitled "The Ten Commandments for OO Programmers". They
>>>could apply almost verbatim to CLOS programmers...

>These commandments are almost impossible to understand for non-native 
>english speakers. Maybe it would be a fine goal to write them down in 
>modern english. Substance over style please.

I had no real problems.

Kind regards,

Hannah.
From: Ray Dillinger
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <cOLYc.11099$54.152290@typhoon.sonic.net>
Reini Urban wrote:
> ·········@random-state.net schrieb:
> 
>> Pascal Bourguignon <····@thalassa.informatimago.com> wrote:
>>
>>> It could be entitled "The Ten Commandments for OO Programmers". They
>>> could apply almost verbatim to CLOS programmers...
> 
> 
> These commandments are almost impossible to understand for non-native 
> english speakers. Maybe it would be a fine goal to write them down in 
> modern english. Substance over style please.


Well, okay.  As a public service and a courtesy....  English
has obsolete styles and huge vocabulary, and I know how much
of a problem strange styles are in languages you're struggling
with (I have such problems in French).  If you can spare the
effort to read the group in English, it's worth the courtesy
to help make it possible.

[NOTE:  I'm going to explain and paraphrase the "commandments"
  below, even giving context and rationale for some; this
  doesn't imply that I agree with all of them.  In fact, I'm
  not personally such a huge fan of OO; it's a technique that's
  frequently useful, not, to me, a virtue or the One True Design
  Philosophy.]


"1.  Thou shalt not rely solely on the compiler-generated default
  methods for construction, destruction, copy construction, or assignment
  for any but the simplest of classes. Thou shalt scrupulously forge
  these "foremost four" methods for any non-trivial class, yea, even
  though thy implementation be but trivial. Further, thou shalt
  declare and define thy destructor as virtual such that others may
  become heir to the fruits of your labors with ease."

Don't rely on compiler-generated default methods for your
constructors, destructors, copy constructors, or assignments.
You can make an exception to the rule if the class is so simple
as to be 'uninteresting' but for most cases, actually write
implementations for all of these methods, even if the
implementations are one-liners.  Also, make sure the destructor
is virtual, so that inheritance works and avoids obscure bugs
if someone subclasses your class.

"2. Thou shalt not violate the "is-a" rule by abusing the inheritance
  mechanism for thine own twisted perversions. Denounce with vigor the
  primordial OO publications wherein this sinful behavior was
  epitomized."

Don't use the inheritance mechanism to make a subclass inherit
behavior from a class unless every member of that subclass is
also, properly speaking, a member of the class.  Remember those
early textbooks that showed examples where people derived new
types promiscuously, without caring whether members of those
new types were actually members of the types derived from?  They
were wrong, and it's now our job to help correct the mistake
by telling people they were wrong.

  "3. Thou shalt not rely on any implementation-dependent behavior of a
   compiler, operating system, nor hardware environment, lest your code be
   forever caged within that dungeon whilst others code scampers unfettered
   through architectures as yet undreamt ···@

Most language implementations offer facilities that depend on
particular implementation strategies, or on the underlying
hardware or data representations, which are not gauranteed
by the language standard.  Also, there are lots of places where
undefined behavior in the standard is implemented as some
particular behavior for convenience or succinctness in a
particular implementation.  Avoid relying on such features,
and your code will be portable to different implementations
and architectures.

"4. Thou shalt not augment the interface of a class at the
  "concrete" level without most prudent deliberation. Such ill-begotten
  practices imprison thy clients unjustly into your classes, and foment
  unspeakable unrest when code maintenance and extension are required.

When you implement data mutators that directly modify data
members of a class, make sure that they represent real operations
appropriate to the kind of object the class models.  If you
provide lower-level operations or mutators, the class is
easier to write and superficially more "flexible" in that
you can use knowledge about its internal representation to
implement operations that aren't among those the class
designer considered.  However, if you use such an interface
without thinking carefully about it, you may inadvertently
violate consistency or other constraints.  Therefore,
consider your class interfaces carefully, and don't provide
mutators that can be used to leave it in some state that does
not make sense.  If you do provide such interfaces, then code
that uses your classes, even if it works, is likely to be
needlessly complex, doing things outside the class that ought
to be done inside it, and will likely cause trouble when
people have to extend or change it.

  "5. Thou shalt restrict thy friendship to truly worthy
   contemporaries. Beware, for thou art exposing thyself wellnigh as
   rudely as from a trench coat."

In C++, a class can be declared as having "friends" --
other classes that are permitted to change the private
data of its members.  Be careful when declaring something
to be your class' "friend" - it's frequently inappropriate.

"6. Thou shalt not abuse your implementation data by making it public or
  static except in the rarest of circumstances. Thy bits are thine
  own; share them not with others."

It's not usually the right thing to make the data members
of the class public or static; be absolutely sure you know
what you're doing before making such a declaration.


"7. Thou shalt not suffer dangling pointers or references to be harbored
  within your objects. These are nefarious and precarious agents of
  random and wanton destruction. While ye may escape their wrath, thy
  fellow programmer may verily be ravaged by them."

Don't, ever, under any circumstances, allow pointers to be
stored in your object if they might, under any circumstances,
be made stale by something outside your object. Pointers can go
stale (become "dangling pointers") without warning in C++,
because something may be explicitly destroyed and its space
free'd by something using another pointer to the same object.
The same space may even be reallocated to something else
entirely, even though you still have a pointer to it.  If
you use such a pointer after it goes stale, your program
loses - it may crash, do something horrible to another object
inadvertently, or develop random nondeterministic errors that
depend on where the memory allocator put things.

[In Lisps, you don't get this problem.  Garbage collection is
a wonderful thing, and beyond a certain level of program
complexity, a necessary thing.]


  "8. Thou shalt make use of available class libraries as conscientiously
   as possible. Code reuse, not just thine own but that of your clients as
   well, is the holy grail of OO. A seemly set of class libraries will put
   you on a path where you may be enlightened."

Try to avoid implementing stuff that's already been implemented.
Constant use, for a lot of different purposes, will lead to more
general class libraries, which are in turn more useful.  Moreover,
constantly using classes, even if those classes are not designed
for your application, will make you a better (more general)
class designer, because it will make you aware of the issues and
difficulties that poor class design causes.

  "9. Thou shalt forever forswear the use of the vile printf/scanf, rather
   favoring the flowing streams. Cast off thy vile C cloak and partake of
   the wondrous fruit of flexible and extensible IO."

C used printf and scanf to do I/O imperatively.  C++ has stream
I/O, which is somewhat more OO and flexible, especially as
regards user-defined types and classes.  It has become
something of a political issue among C++ coders to be angry
about people's occasional use of C's I/O routines, even in
situations where those routines are entirely adequate; not
particularly because it causes problems, but because they
consider it obsolete and inferior and believe that all
traces of C thinking must be eradicated.


"10. Thou shalt avoid designing "big" classes--classes with both an
  unseemly abundance of instance data and tortuosly complicated
  interfaces. Such accursed classes are the unclean and unwieldy
  result of poor design. Be chastened, seek truth, and design
  again, that thy userid may be enshrined among the enumeration
  of the most purely virtuous."

Try to keep classes small and simple.  Big, unweildy classes
with too much stuff going on and ferociously complicated
interfaces are usually the products of poor design, and will
make life harder for people.  It will also make them think of
you as a loser and an incompetent class designer.  So don't
make such classes.
From: Pascal Bourguignon
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <87657a2do3.fsf@thalassa.informatimago.com>
·········@random-state.net writes:

> Pascal Bourguignon <····@thalassa.informatimago.com> wrote:
> 
> > It could be entitled "The Ten Commandments for OO Programmers". They
> > could apply almost verbatim to CLOS programmers...
> 
> I don't agree. Here's point-by-point:

I'll react only on the following point, but I really feel that these
"The Ten Commandments for OO Programmers" apply equally to CLOS
programmers, your comments nonwithstanding.

>  "7. Thou shalt not suffer dangling pointers or references to be harbored
>   within your objects. These are nefarious and precarious agents of random
>   and wanton destruction. While ye may escape their wrath, thy fellow
>   programmer may verily be ravaged by them."
> 
> Bwhahaaa. ;) "Here's a nickel, go and buy yourself a garbage collector."

  If you never (setf (slot-value some-object 'some-attribute) nil)
  after this some-attribute is no more useful, it won't be  garbage
  collected before some-object, ie. perhaps never.

-- 
__Pascal Bourguignon__                     http://www.informatimago.com/

Our enemies are innovative and resourceful, and so are we. They never
stop thinking about new ways to harm our country and our people, and
neither do we.
From: Coby Beck
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <AusWc.48835$X12.4494@edtnps84>
"Pascal Bourguignon" <····@thalassa.informatimago.com> wrote in message
···················@thalassa.informatimago.com...
> ·········@random-state.net writes:
> >  "7. Thou shalt not suffer dangling pointers or references to be
harbored
> >   within your objects. These are nefarious and precarious agents of
random
> >   and wanton destruction. While ye may escape their wrath, thy fellow
> >   programmer may verily be ravaged by them."
> >
> > Bwhahaaa. ;) "Here's a nickel, go and buy yourself a garbage collector."
>
>   If you never (setf (slot-value some-object 'some-attribute) nil)
>   after this some-attribute is no more useful, it won't be  garbage
>   collected before some-object, ie. perhaps never.

Are you advocating deallocating memory on a data memeber by data member
basis?  That seems very odd to me.  If you are talking about the object that
used to be referenced by by (slot-value some-object 'some-attribute) then
you are mistaken that it will necesarily hang around for the life of
some-object.

-- 
Coby Beck
(remove #\Space "coby 101 @ big pond . com")
From: Pascal Bourguignon
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <87y8k51ov2.fsf@thalassa.informatimago.com>
"Coby Beck" <·····@mercury.bc.ca> writes:

> "Pascal Bourguignon" <····@thalassa.informatimago.com> wrote in message
> ···················@thalassa.informatimago.com...
> > ·········@random-state.net writes:
> > >  "7. Thou shalt not suffer dangling pointers or references to be
> > >   harbored
> > >   within your objects. These are nefarious and precarious agents of
> > >   random
> > >   and wanton destruction. While ye may escape their wrath, thy fellow
> > >   programmer may verily be ravaged by them."
> > >
> > > Bwhahaaa. ;) "Here's a nickel, go and buy yourself a garbage collector."
> >
> >   If you never (setf (slot-value some-object 'some-attribute) nil)
> >   after this some-attribute is no more useful, it won't be  garbage
> >   collected before some-object, ie. perhaps never.
> 
> Are you advocating deallocating memory on a data memeber by data member
> basis?  That seems very odd to me.  If you are talking about the object that
> used to be referenced by by (slot-value some-object 'some-attribute) then
> you are mistaken that it will necesarily hang around for the life of
> some-object.

Commandment 7 relates to the following kind of code:

    // pseudo code: I've not programmed in C++ for several years.
    class example { 
    protected: 
        char* data;
    public: 
        virtual example(void){data=0;}
        virtual void setData(const char* newData){
            dataNoMoreUseful();
            data=newstr(newData);}
        virtual const char* getData(void){
            return(data);}
        virtual void dataNoMoreUseful(void){
            if(data!=0){free(data);}}
        virtual void workWithData(void){
            doSomethingUsefulWith(data);}}


    {example* ex=new example;
        ex->setData(a_pointer_to_a_3_GB_memory_block).
        ex->workWithData();
        ex->dataNoMoreUseful();
        doSomeThingElse();
        return(ex->getData();)} ==> A "dangling" pointer!

In C/C++, the problem appears when you use getData() the second time:
you may get SIGSEGV in the best case, or invalid data at worse.


In CLOS, you'd have this kind of code:

    (defclass example   
        ((data :accessor data))
        (:documentation "For the sake of the argument."))
    (defmethod set-data   ((self example) new-data) (setf (data self) new-data))
    (defmethod get-data   ((self example))          (data self))
    (defmethod work-with-data ((self example))
       (do-something-useful-with (data self)))

So the question is how do you implement data-no-more-useful:

    (defmethod data-no-more-useful ((self example)))

is incorrect.


    (defmethod data-no-more-useful ((self example)) (setf (data self) nil))
    
Is correct, and is what this Seventh Commandment predicates, when
tranlated to CLOS.

    (let ((ex (make-instance 'example)))
        (set-data ex (get-some-3GB-big-data))
        (work-with-data ex)
        (data-no-more-useful ex)
        (do-something-else) ==> With the incorrect implementation, 
                                you get out-of-memory errors.

        (get-data ex)) ==> With the incorrect implementation, you get
                           3GB worth of data, and no problem
                           (contrarily to C/C++) ;
                           With the correct implementation, you get
                           NIL and 3GB free memory once the GC runs.


You can have memory leaks even in Lisp with a garbage collector, in
the sence that data that is no more useful may be kept in some obscure
place somewhere.


-- 
__Pascal Bourguignon__                     http://www.informatimago.com/

Our enemies are innovative and resourceful, and so are we. They never
stop thinking about new ways to harm our country and our people, and
neither do we.
From: neo88
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <6a73bb68.0408231753.57035c7e@posting.google.com>
>     // pseudo code: I've not programmed in C++ for several years.
>     class example { 
>     protected: 
>         char* data;
>     public: 
>         virtual example(void){data=0;}
>         virtual void setData(const char* newData){
>             dataNoMoreUseful();
>             data=newstr(newData);}
>         virtual const char* getData(void){
>             return(data);}
>         virtual void dataNoMoreUseful(void){
>             if(data!=0){free(data);}}
>         virtual void workWithData(void){
>             doSomethingUsefulWith(data);}}
> 
> 
>     {example* ex=new example;
>         ex->setData(a_pointer_to_a_3_GB_memory_block).
>         ex->workWithData();
>         ex->dataNoMoreUseful();
>         doSomeThingElse();
>         return(ex->getData();)} ==> A "dangling" pointer!

Now, I'm not going to point out some of the more obvious errors in
your code, here because you did say you haven't written C++ for a few
yesrs. I did find it interesting to me as a new Lisp programmer
though, that you actually make your C++ code look similar to lisp. By
this I mean that ususally a class in C++ is done like:

class example {
  protected:
    int whatever;
  public:
    float function();
    // blah blah
}

Instead of:

> class example { 
>     protected: 
>         char* data;
>     public: 
>         virtual example(void){data=0;}
>         virtual void setData(const char* newData){
>             dataNoMoreUseful();
>             data=newstr(newData);}
>         virtual const char* getData(void){
>             return(data);}
>         virtual void dataNoMoreUseful(void){
>             if(data!=0){free(data);}}
>         virtual void workWithData(void){
>             doSomethingUsefulWith(data);}}
> 

I just found that interesting, it must hurt experianced Lispers so
much that they actually have to write the code to look like Lisp. I
only hope I can become that good at Lisp.

> You can have memory leaks even in Lisp with a garbage collector, in
> the sence that data that is no more useful may be kept in some obscure
> place somewhere.

AHHHAHAHAHAHA!!!! I knew it! Some people provcliam that you can't, but
I always found it hard to believe.

-- 
May the Source be with you.
neo88 (Philip Haddad)
From: Vassil Nikolov
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <lzllg5l0ug.fsf@janus.vassil.nikolov.names>
······@truevine.net (neo88) writes:

>> [...]
>> You can have memory leaks even in Lisp with a garbage collector, in
>> the sence that data that is no more useful may be kept in some obscure
>> place somewhere.
>
> AHHHAHAHAHAHA!!!! I knew it! Some people provcliam that you can't, but
> I always found it hard to believe.


 The general meaning of memory leak is (roughly speaking), not
 reclaiming/allowing to reclaim memory that could be reclaimed.  I
 don't think anybody has reasonably claimed that Lisp programs cannot
 suffer from that.  However, there is a specific meaning of memory
 leak, having memory that is neither referenced nor available for
 allocation (a not uncommon occurrence in C programs), and that is
 something Lisp programs does not suffer from (and in general,
 programs in languages with (proper) automatic memory management).

 ---Vassil.


-- 
Vassil Nikolov <········@poboxes.com>

Hollerith's Law of Docstrings: Everything can be summarized in 72 bytes.
From: ·········@random-state.net
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <cgf6t5$6of0n$1@midnight.cs.hut.fi>
Pascal Bourguignon <····@thalassa.informatimago.com> wrote:

>>>>  "7. Thou shalt not suffer dangling pointers or references to be
>>>>   harbored within your objects. These are nefarious and precarious 
>>>>   agents of random and wanton destruction. While ye may escape
>>>>   their wrath, thy fellow programmer may verily be ravaged by them."

> In C/C++, the problem appears when you use getData() the second time:
> you may get SIGSEGV in the best case, or invalid data at worse.

> So the question is how do you implement data-no-more-useful:
>     (defmethod data-no-more-useful ((self example)))
> is incorrect.
>     (defmethod data-no-more-useful ((self example)) (setf (data self) nil))
> Is correct, and is what this Seventh Commandment predicates, when
> tranlated to CLOS.

Unwanted references within long-lived objects is a good point, but not
quite the same as dangling pointers: the first keeps the data alive as
long as the object is alive, the latter to -- as you noted -- bogus data
or SIGSEGV of death. I may be nitpicking, but I claim that the first is
not what 7. is about.

Cheers,

 -- Nikodemus                   "Not as clumsy or random as a C++ or Java. 
                             An elegant weapon for a more civilized time."
From: Pascal Bourguignon
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <878yc4zt6f.fsf@thalassa.informatimago.com>
·········@random-state.net writes:

> Pascal Bourguignon <····@thalassa.informatimago.com> wrote:
> 
> >>>>  "7. Thou shalt not suffer dangling pointers or references to be
> >>>>   harbored within your objects. These are nefarious and precarious 
> >>>>   agents of random and wanton destruction. While ye may escape
> >>>>   their wrath, thy fellow programmer may verily be ravaged by them."
> 
> > In C/C++, the problem appears when you use getData() the second time:
> > you may get SIGSEGV in the best case, or invalid data at worse.
> 
> > So the question is how do you implement data-no-more-useful:
> >     (defmethod data-no-more-useful ((self example)))
> > is incorrect.
> >     (defmethod data-no-more-useful ((self example)) (setf (data self) nil))
> > Is correct, and is what this Seventh Commandment predicates, when
> > tranlated to CLOS.
> 
> Unwanted references within long-lived objects is a good point, but not
> quite the same as dangling pointers: the first keeps the data alive as
> long as the object is alive, the latter to -- as you noted -- bogus data
> or SIGSEGV of death. I may be nitpicking, but I claim that the first is
> not what 7. is about.

Ok, they're kind of duals of each other in spaces with or without GC...

-- 
__Pascal Bourguignon__                     http://www.informatimago.com/

Our enemies are innovative and resourceful, and so are we. They never
stop thinking about new ways to harm our country and our people, and
neither do we.
From: Laurence Kramer
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <cgfmeh$j6f$1@wolfberry.srv.cs.cmu.edu>
Pascal Bourguignon wrote:

> 
> In CLOS, you'd have this kind of code:
> 
>     (defclass example   
>         ((data :accessor data))
>         (:documentation "For the sake of the argument."))
>     (defmethod set-data   ((self example) new-data) (setf (data self) new-data))
>     (defmethod get-data   ((self example))          (data self))
>     (defmethod work-with-data ((self example))
>        (do-something-useful-with (data self)))
> 
> So the question is how do you implement data-no-more-useful:
> 
>     (defmethod data-no-more-useful ((self example)))
> 
> is incorrect.
> 
> 
>     (defmethod data-no-more-useful ((self example)) (setf (data self) nil))
>     
> Is correct, and is what this Seventh Commandment predicates, when
> tranlated to CLOS.

Somewhat off-topic, but I'd write data-no-more-useful as:

(defmethod data-no-more-useful ((self example)) (set-data self nil))

This is probably what want if and :before, :after, or :around methods
are defined on set-data.

Larry
From: Pascal Bourguignon
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <87r7pwxxd5.fsf@thalassa.informatimago.com>
Laurence Kramer <·······@cs.cmu.edu> writes:

> Pascal Bourguignon wrote:
> 
> > In CLOS, you'd have this kind of code:
> >     (defclass example           ((data :accessor data))
> >         (:documentation "For the sake of the argument."))
> >     (defmethod set-data   ((self example) new-data) (setf (data self) new-data))
> >     (defmethod get-data   ((self example))          (data self))
> >     (defmethod work-with-data ((self example))
> >        (do-something-useful-with (data self)))
> > So the question is how do you implement data-no-more-useful:
> >     (defmethod data-no-more-useful ((self example)))
> > is incorrect.
> >     (defmethod data-no-more-useful ((self example)) (setf (data
> > self) nil))
> >     Is correct, and is what this Seventh Commandment predicates, when
> > tranlated to CLOS.
> 
> Somewhat off-topic, but I'd write data-no-more-useful as:
> 
> (defmethod data-no-more-useful ((self example)) (set-data self nil))
> 
> This is probably what want if and :before, :after, or :around methods
> are defined on set-data.

It depends.  set-data may check for some assertions and validate the
arguments. nil may not be accepted.  What if the data is actually a
structure or an array of which only the slots or elements are to be
forgotten?  If you don't need this kind of overhead mechanism, the why
bother with CLOS? ;-)

-- 
__Pascal Bourguignon__                     http://www.informatimago.com/

Our enemies are innovative and resourceful, and so are we. They never
stop thinking about new ways to harm our country and our people, and
neither do we.
From: Joe Marshall
Subject: Re: Ten Commandments for Lisp Programmers
Date: 
Message-ID: <4qmsvfqx.fsf@ccs.neu.edu>
······@truevine.net (neo88) writes:

> I found this a while ago (before I got into Lisp):
> http://rikkus.info/ten_commandments.html
> Entitled "The Ten Commandments for C++ Programmers"
>
> I thought it would be fun if some of the programmers here wrote up
> their top ten. 

1.  Rules and laws are not a replacement for intelligent thought.
    Think before blindly following rules.