(Long winded but with a moral at the end).
After nearly 10 years of C++ working
on a financial software project that was
perpetually stuck in the quagmire
I'd had enough and decided to re-examine
my dearly held paradigms which seem
to spring up everywhere.
I begin by tossing my beloved
"The C++ Programming Language" by
Stroustrup into the wastebasket.
As I rethink some of my C++ adventures,
it begins to dawn on me that I've been sold a
crock of horse manure and until now I've been
buying it book, line(s) and linker.
First we were told to use C++ as just a better C,
that we did not have to use all the wonderful
(but then mysterious) object oriented capacities
and that C++ had magically improved the shortcomings of C.
Next we were told that hierarchies of classes and the
careful use of inheritance and the magical polymorphism
would solve all of our problems.
But, instead, many huge projects were created,
choking on their hierarchies while wasting memory,
disk space and processor cycles with their ponderous
machinery. Ordinary programmer editors were
no longer sufficient to manage the complexities and
complex development environments (all slavishly
following the laughable "Visual IDE") were created.
Still later, we were told by the experts that "Design Patterns"
could dramatically improve our productivity and reduce
errors. The Gang of Four Design Patterns books became
my bible as I merrily crafted factories, observers, singletons
and composites, only occasionally looking
askance at the rather cumbersome mechanisms
which had to be explained by a plethora
of long winded comments (such as "see
this over here gets called later by that over there
and then instantiates this other and..." well
you get the picture) - no problem there until, somewhat vaguely
at first, and then with increasing alarm, I began to suspect
that some of these wonderful "Patterns" seemed to be
workarounds for C++ shortcomings.
Finally, most recently, the brilliant Alexandrescu
delivered his "Intro to Modern C++" whose techniques, however
brilliant and efficacious they might be, most substantially
raised my eyebrows that all might not be as it seems
in the kingdom of C++ because Mr. Alexandrescu,
a universally acknowledged expert, seems to be telling us
that we should forget about inheritance hierarchies and move
to even higher levels of lofty abstractions in which
"delegates" mediate, like the greek gods of old,
in the affairs of classes and we use the compiler preprocessor
(of all things) to do our bidding.
So the time has come to look at a new language
and there is Lisp, quiet and steadfast over the years.
Where are the Artificial Intelligences that we dreamed of
in our youth, the HALs, the intelligent development environments
with whom we could converse and who could advise
us intelligently? It is clear to me now, finally,
that these kinds of things,
still in the far off future, will NEVER come from the world of
C++, Python, Ruby, Smalltalk, Prolog and others of their
ilk. They are only tools for small tasks, and though each
makes pretensions of grandeur, they do not have the
scope (pun intended) for bigger things.
Having traveled down the wrong road for a long time
and now having returned to my starting point,
this other road, the road of Lisp, beckons.
So far, the journey is an exciting one,
the promise seems real and while the rest of the
masses follow the crowds to the realms of C#,
I, for the first time, have a feeling that I'm headed
in the right direction.
To the numerous Lisp posters creators of Lisp
software, books, web sites and other freely available information,
My Thanks.
James Pannozzi
aka
Jimserac
aka
Takuon Soho
>I begin by tossing my beloved
>"The C++ Programming Language" by
>Stroustrup into the wastebasket.
Is it too late to salvage that? I hate to see a good book go to waste.
"Eric Lavigne" <············@gmail.com> writes:
> >I begin by tossing my beloved
> >"The C++ Programming Language" by
> >Stroustrup into the wastebasket.
>
> Is it too late to salvage that? I hate to see a good book go to waste.
No need to throw it away, just raise the monitor up a bit by putting the
book under the base. Thats what I do with all my Win32 manuals and CMMI
documentation.
Gregm
Eric Lavigne wrote:
>> I begin by tossing my beloved
>> "The C++ Programming Language" by
>> Stroustrup into the wastebasket.
>
> Is it too late to salvage that? I hate to see a good book go to waste.
It's a tremendously useful book for those who are compelled
to write a lot of C++, but I don't see any way in which it
can accurately be described as a *good* book. (Love seems
like a curious feeling for even the most diehard C++-head
to have towards it, too.)
--
Gareth McCaughan
.sig under construc
Takuon Soho wrote:
> Having traveled down the wrong road for a long time
> and now having returned to my starting point,
> this other road, the road of Lisp, beckons.
Nice to replace all those design patterns with a couple of macros
and higher-order functions :)
I've never understood how anyone could proclaim that the strategy
pattern is a cool new thing, the peak of modern technology :D
Try "Practical Common Lisp" (google it), if nobody mentioned that
before.
Found it.
Wow, great great stuff.
Thanks for suggesting it.
Tak
"Ulrich Hobelmann" <···········@web.de> wrote in message
····················@individual.net...
> Takuon Soho wrote:
>> Having traveled down the wrong road for a long time
>> and now having returned to my starting point,
>> this other road, the road of Lisp, beckons.
>
> Nice to replace all those design patterns with a couple of macros and
> higher-order functions :)
>
> I've never understood how anyone could proclaim that the strategy pattern
> is a cool new thing, the peak of modern technology :D
>
> Try "Practical Common Lisp" (google it), if nobody mentioned that before.
Takuon Soho wrote:
> Finally, most recently, the brilliant Alexandrescu
> delivered his "Intro to Modern C++" whose techniques, however
> brilliant and efficacious they might be, most substantially
> raised my eyebrows that all might not be as it seems
> in the kingdom of C++ because Mr. Alexandrescu,
> a universally acknowledged expert, seems to be telling us
> that we should forget about inheritance hierarchies and move
> to even higher levels of lofty abstractions in which
> "delegates" mediate, like the greek gods of old,
> in the affairs of classes and we use the compiler preprocessor
> (of all things) to do our bidding.
Reading Alexandrescu's Modern C++ Design is what really ended up turning
me on to Lisp. In Modern C++ Design, an entire chapter is spent on
implementing "typelists", a singly linked list of types, as well as the
primitive operations on these lists, such as first, rest, length, map,
and all the other usual operations. But the syntax is absolutely awful,
and you have to watch out for all the esoteric C++ name lookup rules.
For example, here's the equivalent of the #b read macro in C++
metaprogramming:
> template<unsigned int N>
> struct binary
> {
> static const unsigned int digit = N % 10;
> BOOST_STATIC_ASSERT(digit == 0 || digit == 1);
> static const unsigned int value = digit + (binary<N / 10>::value * 2);
> };
>
> template<>
> struct binary<0>
> {
> static const unsigned int value = 0;
> };
This code uses the convention that each metafunction (a C++ template
class) returns its value in a static const member named value, unless
its return value is a type, in which case it returns it in a typedef
named type. Invoking this metafunction ends up being
binary<1010101>::value, but someone else's metafunction could use the
convention binary<1010101>::return.
Uhg!
Also, C++ has some rather arbitrary limitations on what can be passed to
a template (for example, a static const values' members can not), so you
end up needing to create a duplicate structure that is written for
metaprogramming, as well as re-implement every simple operation for that
structure.
Ugh!
Also, C++ metaprogramming creates tons and tons of temporary types, with
no portable way of telling a compiler that these types are temporary.
Calling CtFactorial<5>::value will create CtFactorial<4>,
CtFactorial<3>, CtFactorial<2>, CtFactorial<1>, and CtFactorial<0>,
wasting memory on the symbol table during compilation, as well as
bloating the object files generated with all these temporary types.
UHG!!!!
Lisp macros, on the other hand, are simple to use, follow the same
conventions as functions, and don't waste space saving intermediate
values unless you explicitly ask for it to. I don't know how anyone can
do any metaprogramming at all in C++.
-- MJF
I noticed my blog was referenced in this thread, but I'm trying to
stay out of this topic because it tends to get me into trouble. I've
been programming in C++ for 10+ years, and I honestly think the
current direction of the language is causing a lot of harm to its long
term viability. I've seriously wondered if C++ is the still the right
language for my work.
I'm not against compile time polymorphism and meta-programming, but I
do think that C++ has some serious flaws in its current
implementation. I feel type propagation and growth are huge issues.
They create (and expose) a lot of needless complexity. Not only that
it increases the size of executables, which I believe has
reprecussions that aren't complete understood. For instance the
Microsoft compilier stops inlining when the size of an object file
hits a certain limit, primarily to improve i-cache affinity.
Templates allow you to hit this limit more quickly. This is rarely
discussed.
In many ways, C++ is becoming a compile version of lisp, with far
worse syntax.
christopher wrote:
> I'm not against compile time polymorphism and meta-programming, but I
> do think that C++ has some serious flaws in its current
> implementation. I feel type propagation and growth are huge issues.
> They create (and expose) a lot of needless complexity. Not only that
> it increases the size of executables, which I believe has
> reprecussions that aren't complete understood. For instance the
> Microsoft compilier stops inlining when the size of an object file
> hits a certain limit, primarily to improve i-cache affinity.
> Templates allow you to hit this limit more quickly. This is rarely
> discussed.
As long as templates are used as something like macros, it's fine.
But usually they are abused to implement generics. Only that
these generics are recompiled every time you use them; they are
only typechecked when you use them (so you only find some bugs
really late). Maybe some template instances are shared by the
linker (I don't know how much of that is done), but it's
definitely not elegant.
Ulrich Hobelmann wrote:
> christopher wrote:
>
>> I'm not against compile time polymorphism and meta-programming, but I
>> do think that C++ has some serious flaws in its current
>> implementation. I feel type propagation and growth are huge issues.
>> They create (and expose) a lot of needless complexity. Not only that
>> it increases the size of executables, which I believe has
>> reprecussions that aren't complete understood. For instance the
>> Microsoft compilier stops inlining when the size of an object file
>> hits a certain limit, primarily to improve i-cache affinity. Templates
>> allow you to hit this limit more quickly. This is rarely
>> discussed.
>
> As long as templates are used as something like macros, it's fine. But
> usually they are abused to implement generics. Only that these generics
> are recompiled every time you use them; they are only typechecked when
> you use them (so you only find some bugs really late). Maybe some
> template instances are shared by the linker (I don't know how much of
> that is done), but it's definitely not elegant.
I don't know, it doesn't seem like you could get all the desired
features of C++ templates without generating oodles of code. Since C++
functions are pass by value, even something as simple as a function call
could not be shared -- the size of the memory block to copy would be
different between most instantiations. I'm pretty sure that is why C#
shared generic code between different reference types but not between
different value types.
-- MJF
··········@yahoo.com (christopher) writes:
> In many ways, C++ is becoming a compile version of lisp, with far
> worse syntax.
I've noticed for some time now that C++ has the highly dubious
distinction of the language itself becoming an example of Greenspun's
Tenth. Even worse, I don't think anybody involved even understands
this. Pretty sad, really.
/Jon
--
'j' - a n t h o n y at romeo/charley/november com
I agree about inconvenience and limitations of template metaprogramming
in general. But one of my colleagues adviced just to use enums to
prevent object file bloating at all:
template<unsigned int N>
struct binary
{
enum { digit = N % 10 };
enum { value = digit + (binary<N / 10>::value * 2) };
};
template<>
struct binary<0>
{
enum { value = 0 };
};
Though it will not work for floats.
Takuon Soho wrote:
> Finally, most recently, the brilliant Alexandrescu
> delivered his "Intro to Modern C++" whose techniques, however
> brilliant and efficacious they might be, most substantially
> raised my eyebrows that all might not be as it seems
> in the kingdom of C++ because Mr. Alexandrescu,
> a universally acknowledged expert, seems to be telling us
> that we should forget about inheritance hierarchies and move
> to even higher levels of lofty abstractions in which
> "delegates" mediate, like the greek gods of old,
> in the affairs of classes and we use the compiler preprocessor
> (of all things) to do our bidding.
Cool. What are they trying to get out of the preprocessor? Macrology?
Do templates also sleep with the fish?
kt
--
Cells? Cello? Cells-Gtk?: http://www.common-lisp.net/project/cells/
Why Lisp? http://lisp.tech.coop/RtL%20Highlight%20Film
"Doctor, I wrestled with reality for forty years, and I am happy to
state that I finally won out over it." -- Elwood P. Dowd
Kenny Tilton <·······@nyc.rr.com> writes:
> Takuon Soho wrote:
>
> > Finally, most recently, the brilliant Alexandrescu
> > delivered his "Intro to Modern C++" whose techniques, however
> > brilliant and efficacious they might be, most substantially
> > raised my eyebrows that all might not be as it seems
> > in the kingdom of C++ because Mr. Alexandrescu,
> > a universally acknowledged expert, seems to be telling us
> > that we should forget about inheritance hierarchies and move
> > to even higher levels of lofty abstractions in which
> > "delegates" mediate, like the greek gods of old,
> > in the affairs of classes and we use the compiler preprocessor
> > (of all things) to do our bidding.
>
> Cool. What are they trying to get out of the preprocessor? Macrology?
>
> Do templates also sleep with the fish?
Macrology, more or less. But the horror of it all is that everything
gets done with templates. Template metaprogramming lets you program
in what has to be the ugliest purely functional language ever. You
get a language with heap-allocated frames where AFAICT, garbage
collection is forbidden. And while the template metalanguage is
turing-complete, the only conditional you have is
pattern-matching-on-function-call[*]. You do thankfully get integers, so
there's no mucking around with Church numerals, but you have to build
your own cons cells, so they aren't likely to work with anyone else's.
Not to mention mapcar, map_inheritance_tree, etc. The reason it seems
worth it, is you can, eg, compute your class heirarchy at compile
time.
What amazes me is how these very intelligent C++ programmers who came
up with these techniques didn't run screaming "this can't be the right
way to do things!" A lot of people can live with things, even if they
don't like them, but I think being happy with C++ must take quite a
lack of critical thinking.
[*] In Lisp terms, imagine a Lisp with no setq, where all function
calls are memoized, and with funky complex lambda lists like:
(defugly nodes-in-tree (nil)
0)
(defugly nodes-in-tree ((x . y))
(+ (nodes-in-tree x) (nodes-in-tree y)))
(defugly nodes-in-tree (atom)
1)
On 05 Apr 2005 02:21:10 -0700, ···@conquest.OCF.Berkeley.EDU (Thomas
F. Burdick) wrote:
>What amazes me is how these very intelligent C++ programmers who came
>up with these techniques didn't run screaming "this can't be the right
>way to do things!"
This explains it pretty well:
Template programming has become a mental game for those who want to be
C++ giants. It is a proving ground. C++ templates are not a
meta-programming language. Those that use templates for advanced meta
programming are abusing a side effect of a language construct. The
fact that the syntax is so obtuse (because it was never intended to be
used in this way) provides a way to prove mental prowess.
from http://www.baus.net/optimizationcounter.html
I quite agree.
I first became skeptical 5 years ago when I first started using the c++ STL
but the collection classes were so useful I decided to accept the
rather curious notation and move full scale ahead.
After falling in numerous potholes, I found a chap on the c++ newsgroups
named Igor Tandetnik who would answer your questions or at least
point you in the right direction and with his invaluable help (and that of
others
along with the books). And yes, I fell into the old trick about using
double angle brackets >> in a template expression and not realizing
that it would not compile because it was being mistaken for something
else and that you had to put spaces between them - a sure sign of syntactic
confusion.
I was soon merrily using vectors, sets and multisets with abandon and only
occasionally noticing, especially when I came back to the code after some
months,
what an utterly ugly looking mess it all was.
I begin to see how Common Lisp has analogues for all of these things.
The "Practical Common Lisp book", whoose preliminary drafts I have been
reading
have proved enormously helpful and impressive.
But most helpful to me, so far, are those Lisp posters who also know c++ and
have
explained, as in this thread, Lisp constructs in terms of (perhaps inferior
or laboriously expressed) c++ constructs.
This might very well be the theme of some forthcomming Lisp book with a
title
something like "Lisp for the c++ Deluded".
Thanks Again
Jim Pannozzi
Tak
"Fernando" <···@easyjob.net> wrote in message
·······································@4ax.com...
> On 05 Apr 2005 02:21:10 -0700, ···@conquest.OCF.Berkeley.EDU (Thomas
> F. Burdick) wrote:
>
>
>
>>What amazes me is how these very intelligent C++ programmers who came
>>up with these techniques didn't run screaming "this can't be the right
>>way to do things!"
>
> This explains it pretty well:
>
> Template programming has become a mental game for those who want to be
> C++ giants. It is a proving ground. C++ templates are not a
> meta-programming language. Those that use templates for advanced meta
> programming are abusing a side effect of a language construct. The
> fact that the syntax is so obtuse (because it was never intended to be
> used in this way) provides a way to prove mental prowess.
>
> from http://www.baus.net/optimizationcounter.html
Thomas F. Burdick wrote:
<snip>
> What amazes me is how these very intelligent C++ programmers who came
> up with these techniques didn't run screaming "this can't be the right
> way to do things!" A lot of people can live with things, even if they
> don't like them, but I think being happy with C++ must take quite a
> lack of critical thinking.
Hasn't Java come to that point as well with the introduction of 1.5,
generics, iterators, and more?
Thomas Gagne wrote:
> Thomas F. Burdick wrote:
> <snip>
>
>> What amazes me is how these very intelligent C++ programmers who came
>> up with these techniques didn't run screaming "this can't be the right
>> way to do things!" A lot of people can live with things, even if they
>> don't like them, but I think being happy with C++ must take quite a
>> lack of critical thinking.
>
>
> Hasn't Java come to that point as well with the introduction of 1.5,
> generics, iterators, and more?
I think Java is still pretty simple, and the various syntax
enhancements only provide a bit of sugar for commonly used idioms
as well as typechecking in the compiler. To see how much they
enhance Java power-wise think of them as Lisp macros ;)
The funny thing is that even though the compiler gets additional
typechecking and though the runtime (VM) got revamped because of
some threading stuff, AFAIK the VM still does its paranoid
typecasting (and therefore checking) at runtime... Java is a
gigantic patchwork of ad-hoc solutions to popular programming
problems.
C++ templates allegedly allow real meta-programming (that Thomas
Burdick refered to), although I never looked into them -- IMHO C++
is only good as a small, nice enhanced version of C, but I still
prefer C (better control ever memory) :)
Ulrich Hobelmann wrote:
> Thomas Gagne wrote:
>
>> Hasn't Java come to that point as well with the introduction of 1.5,
>> generics, iterators, and more?
>
> I think Java is still pretty simple, and the various syntax enhancements
> only provide a bit of sugar for commonly used idioms as well as
> typechecking in the compiler.
I don't think that Java is the simple language that it once was. For
example, read the entries from 9-19-04 to 10-18-04 at
http://www.mindview.net/WebLog
Pascal
--
2nd European Lisp and Scheme Workshop
July 26 - Glasgow, Scotland - co-located with ECOOP 2005
http://lisp-ecoop05.bknr.net/
From: Kick Damien-DKICK1
Subject: Re: Former C++ Programmer Approaches Lisp
Date:
Message-ID: <ds17jh6cbb1.fsf@motorola.com>
···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) writes:
> Kenny Tilton <·······@nyc.rr.com> writes:
>
>> Takuon Soho wrote:
>>
>> > Finally, most recently, the brilliant Alexandrescu delivered his
>> > "Intro to Modern C++" whose techniques [...] seems to be telling
>> > us that we should forget about inheritance hierarchies and move
>> > to [...] abstractions in which "delegates" mediate [...] in the
>> > affairs of classes and we use the compiler preprocessor [...].
>>
>> Cool. What are they trying to get out of the preprocessor?
>> Macrology?
>
> Macrology, more or less. But the horror of it all is that everything
> gets done with templates. Template metaprogramming lets you program
> in what has to be the ugliest purely functional language ever. [...]
<nod> Alexandrescu does use C-style macros for some things but the
majority of what he does uses template meta-programming.
> [...] You do thankfully get integers, so there's no mucking around
> with Church numerals, but you have to build your own cons cells, so
> they aren't likely to work with anyone else's. Not to mention
> mapcar, map_inheritance_tree, etc. The reason it seems worth it, is
> you can, eg, compute your class heirarchy at compile time.
Well, personally, if I ever was to delve into template
meta-programming, personally I would use the Boost template
meta-programming library
<http://www.boost.org/libs/mpl/doc/index.html> instead of rolling my
own. While the low level template meta-programming techniques are
pretty nasty, people are building de facto higher level abstractions
on top of them.
> What amazes me is how these very intelligent C++ programmers who
> came up with these techniques didn't run screaming "this can't be
> the right way to do things!" A lot of people can live with things,
> even if they don't like them, but I think being happy with C++ must
> take quite a lack of critical thinking.
Well, again, as someone who writes C++ to make a living and has little
to no chance of convincing anyone that Common Lisp would be a good
choice, even though I have started writing little Lisp utilities
whenever I get the chance, I would rather be able to use something
like Boost's Lambda <http://www.boost.org/doc/html/lambda.html> than
run away from it screaming because it's implemented with the ugliest
purely functional language ever. Of course, the thing that really
gets me personally is not the "ugliness" of template meta-programming,
but rather that just about every compiler with which I've had to deal
over the past 5+ years is far enough away from the ISO standard that
most/many of these libraries break against the compiler.
Kick Damien-DKICK1 <······@motorola.com> writes:
> ···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) writes:
>
> > What amazes me is how these very intelligent C++ programmers who
> > came up with these techniques didn't run screaming "this can't be
> > the right way to do things!" A lot of people can live with things,
> > even if they don't like them, but I think being happy with C++ must
> > take quite a lack of critical thinking.
>
> Well, again, as someone who writes C++ to make a living and has little
> to no chance of convincing anyone that Common Lisp would be a good
> choice
You're not who I was talking about there. I understand trying to use
the best tools you're allowed to for a job -- in the past, I've built
up significant collections of utilities in Perl and C++. I also ran
screaming from C++ because, although I could do a lot of what I
wanted, it felt like I was constantly abusing the language in order to
do so. Alexandrescu, for example, appears to enoy C++. That's what I
find bizzare.
--
/|_ .-----------------------.
,' .\ / | Free Mumia Abu-Jamal! |
,--' _,' | Abolish the racist |
/ / | death penalty! |
( -. | `-----------------------'
| ) |
(`-. '--.)
`. )----'
···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) writes:
> You're not who I was talking about there. I understand trying to use
> the best tools you're allowed to for a job -- in the past, I've built
> up significant collections of utilities in Perl and C++. I also ran
> screaming from C++ because, although I could do a lot of what I
> wanted, it felt like I was constantly abusing the language in order to
> do so. Alexandrescu, for example, appears to enoy C++. That's what I
> find bizzare.
If you want an example where people abuse CL look at the paper "Fast
floating point processing in CL" by Fateman et al: The authors want to
use CL for numerical codes. In order to make the code run acceptably
fast they propose various tricks. Besides avoiding 2D arrays the
nicest trick is to put all variables in one large array of floats.
Instead of variable "x" you would use "(aref the-large-array
position-of-x)" throughout your code. I concede that the authors
noted that this trick would alter the readability of the code and
might be more useful in a compiler.
Matthias wrote:
> ···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) writes:
>
>
>>You're not who I was talking about there. I understand trying to use
>>the best tools you're allowed to for a job -- in the past, I've built
>>up significant collections of utilities in Perl and C++. I also ran
>>screaming from C++ because, although I could do a lot of what I
>>wanted, it felt like I was constantly abusing the language in order to
>>do so. Alexandrescu, for example, appears to enoy C++. That's what I
>>find bizzare.
>
>
> If you want an example where people abuse CL look at the paper "Fast
> floating point processing in CL" by Fateman et al: The authors want to
> use CL for numerical codes. In order to make the code run acceptably
> fast they propose various tricks. Besides avoiding 2D arrays the
> nicest trick is to put all variables in one large array of floats.
> Instead of variable "x" you would use "(aref the-large-array
> position-of-x)" throughout your code. I concede that the authors
> noted that this trick would alter the readability of the code and
> might be more useful in a compiler.
>
Sounds like a job for macrology.
--
Kenny
Why Lisp? http://lisp.tech.coop/RtL%20Highlight%20Film
"If you plan to enter text which our system might consider to be
obscene, check here to certify that you are old enough to hear the
resulting output." -- Bell Labs text-to-speech interactive Web page
From: Marco Baringer
Subject: Re: Former C++ Programmer Approaches Lisp
Date:
Message-ID: <m264wnskym.fsf@soma.local>
Matthias <··@spam.please> writes:
> If you want an example where people abuse CL look at the paper "Fast
> floating point processing in CL" by Fateman et al: The authors want to
> use CL for numerical codes. In order to make the code run acceptably
> fast they propose various tricks. Besides avoiding 2D arrays the
> nicest trick is to put all variables in one large array of floats.
> Instead of variable "x" you would use "(aref the-large-array
> position-of-x)" throughout your code. I concede that the authors
> noted that this trick would alter the readability of the code and
> might be more useful in a compiler.
and then there are people who do this:
http://vorlon.cwru.edu/~beer/Software/FPC-PPC/FPC-PPC-DOC-0.21.txt
--
-Marco
Ring the bells that still can ring.
Forget the perfect offering.
There is a crack in everything.
That's how the light gets in.
-Leonard Cohen
"Marco Baringer" <··@bese.it> writes:
> Matthias <··@spam.please> writes:
>
> > If you want an example where people abuse CL look at the paper "Fast
> > floating point processing in CL" by Fateman et al: The authors want to
> > use CL for numerical codes. In order to make the code run acceptably
> > fast they propose various tricks. Besides avoiding 2D arrays the
> > nicest trick is to put all variables in one large array of floats.
> > Instead of variable "x" you would use "(aref the-large-array
> > position-of-x)" throughout your code. I concede that the authors
> > noted that this trick would alter the readability of the code and
> > might be more useful in a compiler.
>
> and then there are people who do this:
>
> http://vorlon.cwru.edu/~beer/Software/FPC-PPC/FPC-PPC-DOC-0.21.txt
Sounds like implementing C within CL:
] 1) Register usage could be significantly improved with a
] little def/use analysis. This would increase the complexity ...
]
] 2) I've wrestled with how much if any error checking to do in
] double functions and expressions. On the one hand, checking ...
]
] 3) When FPC encounters irrational functions, it currently produces
] calls to the corresponding C math library functions. ...
]
] 4) I've also toyed a bit with adding a C parser to optionally
] allow double expressions to be given in infix form. This would...
Any C++ compiler gives you 1-4 already. Plus static type checking
(good thing here: you don't risk wrong results if you accidentally
type "0" instead of "0.0d"), decent error reporting, and support for
the latest vectorization extensions of your favorite CPU vendor.
I admit that it's cool to get these features in CL. Writing your
numerics in C/C++/Fortran (or generating their code as some colleagues
of mine do) and interfacing them to CL feels still easier to me.
From: Marco Baringer
Subject: Re: Former C++ Programmer Approaches Lisp
Date:
Message-ID: <m2y89jphd6.fsf@soma.local>
Matthias <··@spam.please> writes:
> > If you want an example where people abuse CL look at the paper "Fast
> > floating point processing in CL" by Fateman et al: The authors want to
> > use CL for numerical codes. In order to make the code run acceptably
> > fast they propose various tricks. Besides avoiding 2D arrays the
> > nicest trick is to put all variables in one large array of floats.
> > Instead of variable "x" you would use "(aref the-large-array
> > position-of-x)" throughout your code. I concede that the authors
> > noted that this trick would alter the readability of the code and
> > might be more useful in a compiler.
[snip]
> I admit that it's cool to get these features in CL. Writing your
> numerics in C/C++/Fortran (or generating their code as some colleagues
> of mine do) and interfacing them to CL feels still easier to me.
my point was not that CL was better at C's job than C, my point was
that the example you used in the preceding email was a pretty bad
example and that it is easy to do much better than that.
--
-Marco
Ring the bells that still can ring.
Forget the perfect offering.
There is a crack in everything.
That's how the light gets in.
-Leonard Cohen
From: Kick Damien-DKICK1
Subject: Re: Former C++ Programmer Approaches Lisp
Date:
Message-ID: <ds1d5qoap7o.fsf@motorola.com>
···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) writes:
> Kick Damien-DKICK1 <······@motorola.com> writes:
>
>> ···@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) writes:
>>
>> > What amazes me is how these very intelligent C++ programmers who
>> > came up with these techniques didn't run screaming "this can't be
>> > the right way to do things!" [...]
>>
>> Well, again, as someone who writes C++ to make a living and has
>> little to no chance of convincing anyone that Common Lisp would be
>> a good choice [...]
>
> [...] Alexandrescu, for example, appears to enoy C++. That's what I
> find bizzare.
Well, I'm glad that somebody does and I'd still rather write a large
system in C++ than in C <smile>. Not only so that I can make use of
the libraries, techniques, etc., that they produce but also because
this is how I had my interest in Lisp rekindled. I hadn't really
thought about Lisp since university until I started reading Meyers and
Alexandrescu writing about multiple dispatch and how CLOS (of course
CLOS was never mentioned in my college course) supported it already.
Somewhere I've run across a Guy Steele quote about how Java was an
attempt to drag the C++ programmers halfway to Lisp. I think it's
interesting that in my case it was C++ folks borrowing ideas from Lisp
and implemeting approximations thereof that fully dragged me away from
Java and back to Lisp, though it wasn't too hard because I think I've
always had many of the same misgivings that lead to Paul Graham's
malaise about Java <http://tinyurl.com/7m42y>.
Hello Takuon,
I've been in a similar situation. All we use at work is C++, as the
end-all and be-all of design. And the next big project will be moving
to C#.
Question: how do you translate OOP to Lisp? For example, for
delegates, inheritance, etc.? We have a number of components that
share common functionality, and currently we do that with C++. How
would Lisp do it?
··········@gmail.com wrote:
> Hello Takuon,
>
> I've been in a similar situation. All we use at work is C++, as the
> end-all and be-all of design. And the next big project will be moving
> to C#.
>
> Question: how do you translate OOP to Lisp?
Sorry, that is not a question. CLOS (the Lisp OOP) is the superset of
any OOP.
> For example, for
> delegates, inheritance, etc.?
Delegates are singly-inhertant OOPs way of saying, "Sh*t, we should have
supported multiple inheritance". I now bequeath upon the universe
Tilton's Law of OO Design:
Real-world classes are orthonogal. Define them by multiply inheriting
from singly inheritant hierarchies dedicated to narrow functional
requirements. ie, Chop up the functionality you need into so many singly
inheritant class hierarchies, then define classes which inherit from
exactly one class from each singly inheritant class tree.
> We have a number of components that
> share common functionality, and currently we do that with C++. How
> would Lisp do it?
The same, only better. ie. You obviously have no idea what CLOS can do,
so study up a little and ask again. I do not mean that in a demeaning
way, just as sound advice. You /totally/ need to learn a little CLOS if
you are asking such a question.
kt
--
Cells? Cello? Cells-Gtk?: http://www.common-lisp.net/project/cells/
Why Lisp? http://lisp.tech.coop/RtL%20Highlight%20Film
"Doctor, I wrestled with reality for forty years, and I am happy to
state that I finally won out over it." -- Elwood P. Dowd
Kenny Tilton wrote:
> ··········@gmail.com wrote:
> > Hello Takuon,
> >
> > I've been in a similar situation. All we use at work is C++, as
the
> > end-all and be-all of design. And the next big project will be
moving
> > to C#.
> >
> > Question: how do you translate OOP to Lisp?
>
> Sorry, that is not a question. CLOS (the Lisp OOP) is the superset of
> any OOP.
Okay, I see. What I was wondering is if Lisp has a better way of
handling so-called OO problems than using objects. Is CLOS just a way
to give Lisp users OOP, or is it really a complementary part of the
language that does things Lisp could not do before?
> requirements. ie, Chop up the functionality you need into so many
singly
> inheritant class hierarchies, then define classes which inherit from
> exactly one class from each singly inheritant class tree.
That sounds intriguing.
> The same, only better. ie. You obviously have no idea what CLOS can
do,
> so study up a little and ask again. I do not mean that in a demeaning
> way, just as sound advice. You /totally/ need to learn a little CLOS
if
> you are asking such a question.
I agree. Again, I was just wondering if CLOS was added to please those
wanted OOP, or is it really a complementary modern feature that extends
the language in new (and better) ways?
jonathon wrote:
> Kenny Tilton wrote:
>
>>··········@gmail.com wrote:
>>
>>>Hello Takuon,
>>>
>>>I've been in a similar situation. All we use at work is C++, as
>
> the
>
>>>end-all and be-all of design. And the next big project will be
>
> moving
>
>>>to C#.
>>>
>>>Question: how do you translate OOP to Lisp?
>>
>>Sorry, that is not a question. CLOS (the Lisp OOP) is the superset of
>
>
>>any OOP.
>
>
> Okay, I see. What I was wondering is if Lisp has a better way of
> handling so-called OO problems than using objects.
Oh, I see. I use CLOS so much that I consider it part of Lisp. And it is
in the CL spec, but I get your distinction.
> Is CLOS just a way
> to give Lisp users OOP, or is it really a complementary part of the
> language that does things Lisp could not do before?
Well, Paul Graham inter alia feels Lisp does not need OO. [Cool! Google
"graham oo" and hit "I'm feeling lucky".] Only IIRC he does not actually
supply the alternative, he just says he never needed OO.
I think in one of his books (or was it Norvig?) he invents an OO-lite in
a couple dozen lines of code, so maybe he avoided OO by rolling his own,
which would be what we used to call non-avoiding avoidance. :)
kenny
--
Cells? Cello? Cells-Gtk?: http://www.common-lisp.net/project/cells/
Why Lisp? http://lisp.tech.coop/RtL%20Highlight%20Film
"Doctor, I wrestled with reality for forty years, and I am happy to
state that I finally won out over it." -- Elwood P. Dowd
Kenny Tilton <·······@nyc.rr.com> writes:
> I think in one of his books (or was it Norvig?) he invents an
> OO-lite in a couple dozen lines of code
That sounds like Chapter 25 of _On Lisp_.
--
Steven E. Harris
jonathon wrote:
> What I was wondering is if Lisp has a better way of
> handling so-called OO problems than using objects. Is CLOS just a way
> to give Lisp users OOP, or is it really a complementary part of the
> language that does things Lisp could not do before?
"Cannot do" is always relative due to Turing equivalence. "Cannot do so
elegantly" is usually more appropriate.
Having said that, I am definitely convinced that Common Lisp has a
better conception of OOP than most other OOP languages. In CLOS, OOP
doesn't revolve around objects but around generic functions. You can use
classes and make instances thereof, which is definitely useful,
especially when taking multiple inheritance and class redefinition into
account.
However, generic functions are at the heart of it all. You don't define
methods in classes, but methods belong to such generic functions. When a
generic function is called, it selects the applicable methods according
to the classes and identities of the passed arguments, and applies them
in the correct order (most specific one first).
This allows you to freely mix functions and generic functions without
noticing that you are "switching paradigms". This also gives you a very
natural integration of multimethods, eql specializers (methods
specialized on objects instead of classes), and method combinations like
before/after/around.
And we haven't talked about the metaobject protocol yet. ;)
You can get a good overview by reading the papers at
http://www.dreamsongs.com/CLOS.html - especially the last two ones.
(They have been written before ANSI Common Lisp was published, so there
are some slight changes in the actual syntax of CLOS than what is
described in those papers.)
Pascal
--
2nd European Lisp and Scheme Workshop
July 26 - Glasgow, Scotland - co-located with ECOOP 2005
http://lisp-ecoop05.bknr.net/
> Having said that, I am definitely convinced that Common Lisp has a
> better conception of OOP than most other OOP languages. In CLOS, OOP
> doesn't revolve around objects but around generic functions. You can
use
> classes and make instances thereof, which is definitely useful,
> especially when taking multiple inheritance and class redefinition
into
> account.
>
> However, generic functions are at the heart of it all. You don't
define
> methods in classes, but methods belong to such generic functions.
When a
> generic function is called, it selects the applicable methods
according
> to the classes and identities of the passed arguments, and applies
them
> in the correct order (most specific one first).
Well, I'm sold. Payday is tomorrow, so I just have to figure out which
books to get to get started.
I think maybe I'll grab 'ANSI Common Lisp' and 'Practical Lisp.'
Any thoughts on 'Successful Lisp' ??
jonathon wrote:
> Well, I'm sold. Payday is tomorrow, so I just have to figure out which
> books to get to get started.
>
> I think maybe I'll grab 'ANSI Common Lisp' and 'Practical Lisp.'
>
> Any thoughts on 'Successful Lisp' ??
All good books, so this is hard to tell. If you want a book that takes
CLOS seriously, though, better avoid Paul Graham's books. (His books are
excellent wrt to macro programming though.)
The other books are available online, so just take a look and decide for
yourself. Peter Norvig's "Patterns of Artificial Intelligence
Programming" is also usually recommended, but is not online.
If you don't mind reading (well-written) specifications, you should also
check out Common Lisp the Language, 2nd Edition by Guy Steele, also
available online. Some of the details have changed in the final ANSI
Common Lisp specification, but that book is still an excellent source of
information. For the "final" word, check out
http://www.lispworks.com/documentation/HyperSpec/index.html or
http://www.franz.com/support/documentation/7.0/ansicl/ansicl.htm which
were derived from the ANSI specification.
Pascal
--
2nd European Lisp and Scheme Workshop
July 26 - Glasgow, Scotland - co-located with ECOOP 2005
http://lisp-ecoop05.bknr.net/
On 4236 September 1993, Pascal Costanza wrote:
> All good books, so this is hard to tell. If you want a book that takes
> CLOS seriously, though, better avoid Paul Graham's books. (His books
> are excellent wrt to macro programming though.)
FWIW, I would also recommend Keene's "Object-Oriented Programming in
Common Lisp", if you can get hold of a copy. It's a good introduction
to CLOS, though it doesn't talk about the MOP.
Holger
--
--- http://www.coling.uni-freiburg.de/~schauer/ ---
"In my day, we wrote games in assembler, uphill 3 miles in the snow each
way, and we liked it, damnit. You're spoilt rotten by options these
days." -- David Golden in comp.lang.lisp
From: Karl A. Krueger
Subject: Re: Former C++ Programmer Approaches Lisp
Date:
Message-ID: <d367tk$guv$1@baldur.whoi.edu>
Holger Schauer <··············@gmx.de> wrote:
> On 4236 September 1993, Pascal Costanza wrote:
>> All good books, so this is hard to tell. If you want a book that takes
>> CLOS seriously, though, better avoid Paul Graham's books. (His books
>> are excellent wrt to macro programming though.)
>
> FWIW, I would also recommend Keene's "Object-Oriented Programming in
> Common Lisp", if you can get hold of a copy. It's a good introduction
> to CLOS, though it doesn't talk about the MOP.
I'll second that recommendation, having recently received a copy of
Keene's book. The level of detail she goes into, I think, would be
especially valuable to someone coming from C++, Java, or another OO
language with a substantially different approach.
--
Karl A. Krueger <········@example.edu> { s/example/whoi/ }
On Thu, 07 Apr 2005 03:56:22 +0000, Kenny Tilton wrote:
> ··········@gmail.com wrote:
>> Question: how do you translate OOP to Lisp?
>
> Sorry, that is not a question. CLOS (the Lisp OOP) is the superset of
> any OOP.
>
>> For example, for
>> delegates, inheritance, etc.?
>
> Delegates are singly-inhertant OOPs way of saying, "Sh*t, we should have
> supported multiple inheritance". I now bequeath upon the universe
> Tilton's Law of OO Design:
I was under the impression that delegates are a patch for a lack of first
class functions, and interfaces a mechanism for getting some multiple
inheritance to a single inheritance language. However, since I'm not that
fond of OO programming (in the guise of languages like Java and C#, Python
does have something going for it though, for a few years I used
wherever I could), I tend to get confused by some of that terminology...
--
Christopher
April's blossoms bloom
Rabbits roam the fields again
An upgrade is due
> I was under the impression that delegates are a patch for a lack of
first
> class functions, and interfaces a mechanism for getting some multiple
> inheritance to a single inheritance language. However, since I'm not
that
> fond of OO programming (in the guise of languages like Java and C#,
Python
> does have something going for it though, for a few years I used
> wherever I could), I tend to get confused by some of that
terminology...
I'm at the 'loving Python' stage myself. And you found everything you
needed when you moved to Lisp?
On Thu, 07 Apr 2005 05:58:50 -0700, jonathon wrote:
>> fond of OO programming (in the guise of languages like Java and C#,
> Python
>> does have something going for it though, for a few years I used
>> wherever I could), I tend to get confused by some of that
> terminology...
>
> I'm at the 'loving Python' stage myself. And you found everything you
> needed when you moved to Lisp?
Well, I've had run-ins with Lisp in the past, but I never could get my
head around it. Then I've had to work with C-like languages a lot, and
forgot about Lisp. After finding and growing to love Python, last year I
did a smallish personal project where I hit Python's limits (well,
probably not really, but metaprogramming in Python can quickly enough
become black magic, and I'm wasn't enough of a wizard to get it working).
After some search I realized I was missing macros, and found incredibly
good books online (On Lisp did blow my mind, and I've also just ordered
Practical Common Lisp), and after not too much time I had a working
program in SBCL where I'd struggled with Python. Sometimes I do miss some
libraries, but mostly I've found good enough or better equivalents for
Lisp, so no problem there. When hacking a quick shell script or
prototyping something for people unfamiliar with Lisp (I never had the
parenthesis problem but most everyone else I know does), I still tend to
use Python though, but my assimilation will probably soon be complete. ;-)
--
Christopher
The blowing wind sent
A cherry blossom falling
New mail has arrived
Christopher Koppler wrote:
> On Thu, 07 Apr 2005 05:58:50 -0700, jonathon wrote:
> After some search I realized I was missing macros, and found
incredibly
> good books online (On Lisp did blow my mind, and I've also just
ordered
> Practical Common Lisp), and after not too much time I had a working
> program in SBCL where I'd struggled with Python. Sometimes I do miss
some
I'm trying to choose an implementation that will run well on FreeBSD
ATM.
> Lisp, so no problem there. When hacking a quick shell script or
> prototyping something for people unfamiliar with Lisp (I never had
the
> parenthesis problem but most everyone else I know does), I still tend
to
> use Python though, but my assimilation will probably soon be
complete. ;-)
That's another question I have. Is it difficult to use Lisp as a
scripting language?
From: Sam Steingold
Subject: Re: Former C++ Programmer Approaches Lisp
Date:
Message-ID: <u3bu1w00n.fsf@gnu.org>
> * jonathon <···········@ovtsbbg.pbz> [2005-04-08 06:59:37 -0700]:
>
> I'm trying to choose an implementation that will run well on FreeBSD
> ATM.
<http://www.freshports.org/lang/clisp/>
> Is it difficult to use Lisp as a scripting language?
<http://clisp.cons.org/impnotes/quickstart.html>
Script execution.
* The script should contain Lisp forms, except in the #! line.
* The file is loaded normally, through the function LOAD (in
particular, the name of the script file, which is $0 in /bin/sh,
can be found in *LOAD-TRUENAME* and *LOAD-PATHNAME*).
* Before it is loaded, the variable EXT:*ARGS* is bound to a list of
strings, representing the arguments given to the Lisp script
(i.e., $1 in /bin/sh becomes (CAR EXT:*ARGS*) etc).
* *STANDARD-INPUT* and *STANDARD-OUTPUT* are bound, as usual, to the
Unix standard input and output. *ERROR-OUTPUT* is bound to the
Unix error output.
* Continuable errors will be turned to warnings (using
EXT:APPEASE-CERRORS).
* Non-continuable errors and Control-C interrupts will terminate the
execution of the Lisp script with an error status (using
EXT:EXIT-ON-ERROR).
* If you wish the script's contents to be compiled during loading,
add -C to the interpreter-arguments.
--
Sam Steingold (http://www.podval.org/~sds) running w2k
<http://www.camera.org> <http://www.memri.org/> <http://www.jihadwatch.org/>
<http://www.mideasttruth.com/> <http://www.dhimmi.com/>
If You Want Breakfast In Bed, Sleep In the Kitchen.
"jonathon" <···········@bigfoot.com> writes:
> Christopher Koppler wrote:
> > On Thu, 07 Apr 2005 05:58:50 -0700, jonathon wrote:
> > After some search I realized I was missing macros, and found
> incredibly
> > good books online (On Lisp did blow my mind, and I've also just
> ordered
> > Practical Common Lisp), and after not too much time I had a working
> > program in SBCL where I'd struggled with Python. Sometimes I do miss
> some
>
> I'm trying to choose an implementation that will run well on FreeBSD
> ATM.
clisp works well on all unix systems.
> > Lisp, so no problem there. When hacking a quick shell script or
> > prototyping something for people unfamiliar with Lisp (I never had
> the
> > parenthesis problem but most everyone else I know does), I still tend
> to
> > use Python though, but my assimilation will probably soon be
> complete. ;-)
>
> That's another question I have. Is it difficult to use Lisp as a
> scripting language?
Nothing easier:
#!/usr/bin/clisp -ansi -q
(dolist (arg ext:*args*)
(if (handler-case (probe-file arg) (error () nil))
(format t "~&~A is a file.~%" arg)
(format t "~&~A is not a file.~%" arg)))
--
__Pascal Bourguignon__ http://www.informatimago.com/
Wanna go outside.
Oh, no! Help! I got outside!
Let me back inside!
"jonathon" <···········@bigfoot.com> writes:
> That's another question I have. Is it difficult to use Lisp as a
> scripting language?
>
Look at the code below, and decide for yourself. This is a script which
sets a random bacground for Gnome, reading a list of images from a file..
(with-disclaimer-about-not-being-a-lisp-guru
#!/usr/bin/clisp -q
(defvar *backdrops-collection*
#p"/home/rv/.gnome2/gthumb/collections/Backdrops.gqv"
"This is where ``gthumb'' stores my Backdrops catalog.
It's just a list of strings, why not use it.")
(defun pick-random (list)
(nth (random (length list) (make-random-state t))
list))
(defun set-background (image)
(ext:run-program
"gconftool-2"
:arguments (list "-t"
"str"
"--set"
"/desktop/gnome/background/picture_filename"
image)))
(defun get-background ()
(read-line
(ext:run-program
"gconftool-2"
:arguments (list "--get"
"/desktop/gnome/background/picture_filename")
:output :stream) nil ""))
(defun random-background ()
(let ((current (get-background)))
(with-open-file (file *backdrops-collection*)
(do ((line (read file nil nil)
(read file nil nil))
(lines nil))
((null line) (set-background
(pick-random (remove current lines
:test #'string=))))
(push line lines)))))
(random-background)
)
--
If in doubt, argue.
Christopher Koppler wrote:
> On Thu, 07 Apr 2005 03:56:22 +0000, Kenny Tilton wrote:
>
>
>>··········@gmail.com wrote:
>
>
>>>Question: how do you translate OOP to Lisp?
>>
>>Sorry, that is not a question. CLOS (the Lisp OOP) is the superset of
>>any OOP.
>>
>>
>>> For example, for
>>>delegates, inheritance, etc.?
>>
>>Delegates are singly-inhertant OOPs way of saying, "Sh*t, we should have
>>supported multiple inheritance". I now bequeath upon the universe
>>Tilton's Law of OO Design:
>
>
> I was under the impression that delegates are a patch for a lack of first
> class functions,
Maybe I misunderstood. The "delegates" I am thinking of are instances of
some other class held as attributes by some delegating instance (of some
other class). The delegate handles certain "messages" we would like the
delegating instance to handle, but it cannot because the messages for
the delegate divide up in a way orthogonal to the delegating class's
division of its main responsibility.
First-class functions do not help here, because we still need
polymorphic dispatch, but in a way orthogonal to the delegator's view of
the world.
>... and interfaces a mechanism for getting some multiple
> inheritance to a single inheritance language.
Interfaces are OOPs' way of saying "Sh*t, we acknowledge the need for
multiple inheritance but this is as close as we can get. Hope ya like it!"
>.. However, since I'm not that
> fond of OO programming (in the guise of languages like Java and C#, Python
> does have something going for it though, for a few years I used
> wherever I could), I tend to get confused by some of that terminology...
Well, you can do a lot with first-class functions. I think PCL uses them
where polymorphism should have been used, at least in one example I
stared at. So I can see where simple delegates (handling just one
message for the delegator) could be replaced by a first-class function.
kenny
--
Cells? Cello? Cells-Gtk?: http://www.common-lisp.net/project/cells/
Why Lisp? http://lisp.tech.coop/RtL%20Highlight%20Film
"Doctor, I wrestled with reality for forty years, and I am happy to
state that I finally won out over it." -- Elwood P. Dowd
Kenny Tilton <·······@nyc.rr.com> writes:
> Interfaces are OOPs' way of saying "Sh*t, we acknowledge the need for
> multiple inheritance but this is as close as we can get. Hope ya like
> it!"
I think this is an overly simplistic way to view interfaces. You can
get yourself into trouble with CLOS if you define a class which
multiply inherits super classes which have conflicting slots. This
situation is exacerbated if, for example, the slots have different
allocation policies. Interfaces compromise by not allowing state to
be multiply inherited. This compromise is not without merit.
Carl Shapiro <·············@panix.com> writes:
>
> Kenny Tilton <·······@nyc.rr.com> writes:
>
> > Interfaces are OOPs' way of saying "Sh*t, we acknowledge the need for
> > multiple inheritance but this is as close as we can get. Hope ya like
> > it!"
>
> I think this is an overly simplistic way to view interfaces. You can
> get yourself into trouble with CLOS if you define a class which
> multiply inherits super classes which have conflicting slots. This
> situation is exacerbated if, for example, the slots have different
> allocation policies. Interfaces compromise by not allowing state to
> be multiply inherited. This compromise is not without merit.
Well, with proper use of namespaces and naming discipline, this is not
supposed to happen. (Yeah, in practice it doesn't always work that
way), but the philosophy is that a slot named by a particular symbol is
supposed to have only one meaning. So one would really ideally have
something like ship:deck and card:deck to differentiate slots that would
otherwise have similar names.
The drawback to interfaces is that if you ever want an interface that
needs to have state, then you have to make sure you add the slots for
that state into your object. And in Java it is even worse, because
interfaces can only contain abstract methods. Which means you have to
implement all the methods for an interface whenever you want to include
it for inheritance. This is not only annoying, but it removes a lot of
the benefit of using OOP in the first place.
--
Thomas A. Russ, USC/Information Sciences Institute
···@sevak.isi.edu (Thomas A. Russ) writes:
> Well, with proper use of namespaces and naming discipline, this is not
> supposed to happen. (Yeah, in practice it doesn't always work that
> way), but the philosophy is that a slot named by a particular symbol is
> supposed to have only one meaning. So one would really ideally have
> something like ship:deck and card:deck to differentiate slots that would
> otherwise have similar names.
Do you have an idea of how many large class hierarchies have actually
been written this way? I don't mean to suggest that these things do
not exist, but I have never encountered such a system. Some of the
most bushy class hierarchies I have encountered are in knowledge bases
which intern all its symbols into one package. This practice is quite
common. It is pretty painful to derive new types; you need to have a
global perspective on the system.
> The drawback to interfaces is that if you ever want an interface that
> needs to have state, then you have to make sure you add the slots for
> that state into your object. And in Java it is even worse, because
> interfaces can only contain abstract methods. Which means you have to
> implement all the methods for an interface whenever you want to include
> it for inheritance. This is not only annoying, but it removes a lot of
> the benefit of using OOP in the first place.
Yes, the Java perspective on interface classes is quite weak and
almost self defeating.
Carl Shapiro wrote:
> ···@sevak.isi.edu (Thomas A. Russ) writes:
>
>>Well, with proper use of namespaces and naming discipline, this is not
>>supposed to happen. (Yeah, in practice it doesn't always work that
>>way), but the philosophy is that a slot named by a particular symbol is
>>supposed to have only one meaning. So one would really ideally have
>>something like ship:deck and card:deck to differentiate slots that would
>>otherwise have similar names.
>
> Do you have an idea of how many large class hierarchies have actually
> been written this way? I don't mean to suggest that these things do
> not exist, but I have never encountered such a system. Some of the
> most bushy class hierarchies I have encountered are in knowledge bases
> which intern all its symbols into one package. This practice is quite
> common. It is pretty painful to derive new types; you need to have a
> global perspective on the system.
Would it be possible to refactor such class hierarchies? I can imagine
some problems there, of course, especially disambiguating between
intentional and non-intentional overridings of slots.
You have stated problems wrt to slots. Does this mean that such problems
don't occur wrt methods in your experience?
Pascal
--
2nd European Lisp and Scheme Workshop
July 26 - Glasgow, Scotland - co-located with ECOOP 2005
http://lisp-ecoop05.bknr.net/
Carl Shapiro wrote:
> Kenny Tilton <·······@nyc.rr.com> writes:
>
>
>>Interfaces are OOPs' way of saying "Sh*t, we acknowledge the need for
>>multiple inheritance but this is as close as we can get. Hope ya like
>>it!"
>
>
> I think this is an overly simplistic way to view interfaces. You can
> get yourself into trouble with CLOS if you define a class which
> multiply inherits super classes which have conflicting slots. This
> situation is exacerbated if, for example, the slots have different
> allocation policies. Interfaces compromise by not allowing state to
> be multiply inherited. This compromise is not without merit.
We give up all the expressive value of MI, put up with the cut-and-paste
madness of Interfaces, all to achieve an artificial discipline saving us
from ourselves (bad OO design), a discipline which could be achieved
anyway with a little moppery?
kenny
--
Cells? Cello? Cells-Gtk?: http://www.common-lisp.net/project/cells/
Why Lisp? http://lisp.tech.coop/RtL%20Highlight%20Film
"Doctor, I wrestled with reality for forty years, and I am happy to
state that I finally won out over it." -- Elwood P. Dowd
Kenny Tilton <·······@nyc.rr.com> writes:
> We give up all the expressive value of MI, put up with the
> cut-and-paste madness of Interfaces, all to achieve an artificial
> discipline saving us from ourselves (bad OO design), a discipline
> which could be achieved anyway with a little moppery?
An interface does not lose all the expressive value of multiple
inheritance, you lose only the ability to multiply inherit state. You
can still multiply inherit functions and contracts to implement
functions.
Its debatable as to whether or not this is worse than what the
contemporary Lisp environments have, which is nothing at all to help
you with this class of problems. This is not a consequence of "bad OO
design". Even good designs need to be adapted an maintained by people
who were not the original authors. If you work with other peoples
class hierarchies you are screwed; there is nothing help to pick up
the slack.
Carl Shapiro wrote:
> Kenny Tilton <·······@nyc.rr.com> writes:
>
>>We give up all the expressive value of MI, put up with the
>>cut-and-paste madness of Interfaces, all to achieve an artificial
>>discipline saving us from ourselves (bad OO design), a discipline
>>which could be achieved anyway with a little moppery?
>
> An interface does not lose all the expressive value of multiple
> inheritance, you lose only the ability to multiply inherit state. You
> can still multiply inherit functions and contracts to implement
> functions.
Which language do you have in mind that allows you to do this?
> Its debatable as to whether or not this is worse than what the
> contemporary Lisp environments have, which is nothing at all to help
> you with this class of problems. This is not a consequence of "bad OO
> design". Even good designs need to be adapted an maintained by people
> who were not the original authors. If you work with other peoples
> class hierarchies you are screwed; there is nothing help to pick up
> the slack.
I think that packages help you to solve name clashes at the root. Or do
you disagree?
Pascal
--
2nd European Lisp and Scheme Workshop
July 26 - Glasgow, Scotland - co-located with ECOOP 2005
http://lisp-ecoop05.bknr.net/
Carl Shapiro wrote:
> Kenny Tilton <·······@nyc.rr.com> writes:
>
>
>>We give up all the expressive value of MI, put up with the
>>cut-and-paste madness of Interfaces, all to achieve an artificial
>>discipline saving us from ourselves (bad OO design), a discipline
>>which could be achieved anyway with a little moppery?
>
>
> An interface does not lose all the expressive value of multiple
> inheritance, you lose only the ability to multiply inherit state. You
> can still multiply inherit functions and contracts to implement
> functions.
>
> Its debatable as to whether or not this is worse than what the
> contemporary Lisp environments have, which is nothing at all to help
> you with this class of problems. This is not a consequence of "bad OO
> design". Even good designs need to be adapted an maintained by people
> who were not the original authors. If you work with other peoples
> class hierarchies you are screwed; there is nothing help to pick up
> the slack.
Who works with Other Peoples Code?! :) Functional suites mebbe, but
class hierarchies off the shelf? Twice? Both proprietary so I cannot get
at the source? Both using the same slot name even though these two
libraries offer different functionality (or why would one class be
inheriting from both?).
This unlikely set of circumstances gets used to justify a lot of dubious
mechanisms, it seems. I will christen it the Hobgoblin Scenario.
kenny
--
Cells? Cello? Cells-Gtk?: http://www.common-lisp.net/project/cells/
Why Lisp? http://lisp.tech.coop/RtL%20Highlight%20Film
"Doctor, I wrestled with reality for forty years, and I am happy to
state that I finally won out over it." -- Elwood P. Dowd
Kenny Tilton <·······@nyc.rr.com> writes:
> Who works with Other Peoples Code?! :) Functional suites mebbe, but
> class hierarchies off the shelf? Twice? Both proprietary so I cannot
> get at the source? Both using the same slot name even though these two
> libraries offer different functionality (or why would one class be
> inheriting from both?).
Most software development time is spent with other peoples code. It
is simply not a viable strategy to have every programmer review every
class in every module when they want to maintain a class hierarchy.
It is also not acceptable to be forced to build firewalls around other
peoples software in order to make simple extensions. Lastly, looking
at source code won't help you when various parts of the system do not
exist until runtime.
> This unlikely set of circumstances gets used to justify a lot of
> dubious mechanisms, it seems. I will christen it the Hobgoblin
> Scenario.
Welcome to the profession of software engineering. Real programmers
spend most of their time working on stuff they did not design and
fixing bugs they did not introduce. Deal with it.
Carl Shapiro <·············@panix.com> writes:
> Most software development time is spent with other peoples code. It
> is simply not a viable strategy to have every programmer review every
> class in every module when they want to maintain a class hierarchy.
Hmm... this does not read as I intended. "...to have every programmer
review... to derive a new class." is more on the mark.
From: Christopher C. Stacy
Subject: Re: Former C++ Programmer Approaches Lisp
Date:
Message-ID: <u7jje2ur6.fsf@news.dtpq.com>
Kenny Tilton <·······@nyc.rr.com> writes:
> Carl Shapiro wrote:
> > Kenny Tilton <·······@nyc.rr.com> writes:
> >
> >>We give up all the expressive value of MI, put up with the
> >>cut-and-paste madness of Interfaces, all to achieve an artificial
> >>discipline saving us from ourselves (bad OO design), a discipline
> >>which could be achieved anyway with a little moppery?
> > An interface does not lose all the expressive value of multiple
> > inheritance, you lose only the ability to multiply inherit state. You
> > can still multiply inherit functions and contracts to implement
> > functions.
> > Its debatable as to whether or not this is worse than what the
> > contemporary Lisp environments have, which is nothing at all to help
> > you with this class of problems. This is not a consequence of "bad OO
> > design". Even good designs need to be adapted an maintained by people
> > who were not the original authors. If you work with other peoples
> > class hierarchies you are screwed; there is nothing help to pick up
> > the slack.
>
> Who works with Other Peoples Code?! :) Functional suites mebbe, but
> class hierarchies off the shelf? Twice? Both proprietary so I cannot
> get at the source? Both using the same slot name even though these two
> libraries offer different functionality (or why would one class be
> inheriting from both?).
>
> This unlikely set of circumstances gets used to justify a lot of
> dubious mechanisms, it seems. I will christen it the Hobgoblin
> Scenario.
Slot names aren't going to conflict with other people's classes,
because the names will be in a different package.
The real problem is the lack of protocol information.
Kenny Tilton wrote:
>
> Christopher Koppler wrote:
>>
>> I was under the impression that delegates are a patch for a lack of first
>> class functions,
>
> Maybe I misunderstood. The "delegates" I am thinking of are instances of
> some other class held as attributes by some delegating instance (of some
> other class). The delegate handles certain "messages" we would like the
> delegating instance to handle, but it cannot because the messages for
> the delegate divide up in a way orthogonal to the delegating class's
> division of its main responsibility.
In C#, delegates are indeed similar to closures or first-class
functions. They additionally remember an object to which a method should
be sent. Googling for "C# delegates" gives you a few links that explain
them.
You are thinking about delegation as in prototype-based languages.
That's a different concept.
Pascal
--
2nd European Lisp and Scheme Workshop
July 26 - Glasgow, Scotland - co-located with ECOOP 2005
http://lisp-ecoop05.bknr.net/
Pascal Costanza wrote:
> Kenny Tilton wrote:
>
>>
>> Christopher Koppler wrote:
>>
>>>
>>> I was under the impression that delegates are a patch for a lack of
>>> first
>>> class functions,
>>
>>
>> Maybe I misunderstood. The "delegates" I am thinking of are instances
>> of some other class held as attributes by some delegating instance (of
>> some other class). The delegate handles certain "messages" we would
>> like the delegating instance to handle, but it cannot because the
>> messages for the delegate divide up in a way orthogonal to the
>> delegating class's division of its main responsibility.
>
>
> In C#, delegates are indeed similar to closures or first-class
> functions. They additionally remember an object to which a method should
> be sent. Googling for "C# delegates" gives you a few links that explain
> them.
Right. Thanks. Delightful the contortions these languages are going thru
to offer their users Lisp.
>
> You are thinking about delegation as in prototype-based languages.
No, I am not. According to the chit-chat here:
http://c2.com/cgi/wiki?WhatIsDelegation
I am thinking about "manual, explicit delegation.
kenny
--
Cells? Cello? Cells-Gtk?: http://www.common-lisp.net/project/cells/
Why Lisp? http://lisp.tech.coop/RtL%20Highlight%20Film
"Doctor, I wrestled with reality for forty years, and I am happy to
state that I finally won out over it." -- Elwood P. Dowd
Kenny Tilton wrote:
>
>
> Pascal Costanza wrote:
>>
>> You are thinking about delegation as in prototype-based languages.
>
> No, I am not. According to the chit-chat here:
>
> http://c2.com/cgi/wiki?WhatIsDelegation
>
> I am thinking about "manual, explicit delegation.
...just when I thought I could read your mind... ;)
Pascal
--
2nd European Lisp and Scheme Workshop
July 26 - Glasgow, Scotland - co-located with ECOOP 2005
http://lisp-ecoop05.bknr.net/
Pascal Costanza <··@p-cos.net> writes:
> Kenny Tilton wrote:
> >
> >
> > Pascal Costanza wrote:
> >>
> >> You are thinking about delegation as in prototype-based languages.
> >
> > No, I am not. According to the chit-chat here:
> >
> > http://c2.com/cgi/wiki?WhatIsDelegation
> >
> > I am thinking about "manual, explicit delegation.
>
> ...just when I thought I could read your mind... ;)
I think you missed: I was thinking of prototype-based object systems.
>>> Delegates are singly-inhertant OOPs way of saying, "Sh*t, we should
>>> have supported multiple inheritance".
>> I was under the impression that delegates are a patch for a lack of
>> first class functions,
Even in presence of multiple-inheritance, delegation has its applications.
You can change the delegate at runtime. In CLOS, you can of course
change the class inheritance graph at runtime, but oftentimes just
switching delegates is simpler and more elegant. (My CLIM is shaky,
but I believe that a graft delegates to its mirror, for example.)
And you can delegate to multiple objects of the same class. Existent
schemes that allow you to inherit twice from the same class (duplica-
ting all of the inherited state) are messy, at best.
I like to think of delegation as being the primitive behind
inheritance. Since it's a primitive, it's less convenient, but also
way more powerful.
> Interfaces are OOPs' way of saying "Sh*t, we acknowledge the need for
> multiple inheritance but this is as close as we can get. Hope ya like
> it!"
Why is it that nobody understand interfaces ;-)
Interfaces are a statically typed language's way of saying that a
category of objects implement a given protocol.
For example, in some Lisp dialects there is no common ancestor to all
the classes that implement the stream protocol. In a strongly typed
language, you'd put all of the stream classes in a single interface --
never mind that there's no common internal structure that would
justify inheriting from a common ancestor.
Juliusz
> Real-world classes are orthonogal. Define them by multiply inheriting
> from singly inheritant hierarchies dedicated to narrow functional
> requirements. ie, Chop up the functionality you need into so many
singly
> inheritant class hierarchies, then define classes which inherit from
> exactly one class from each singly inheritant class tree.
I've been thinking about this, and I have a question.
Does this mean the derived classes would only override methods rather
than adding new ones? It doesn't *seem* to make sense to have the
class tree getting 'wider' with each derived class. Also, it *seems*
the only derived class you would want from each tree would be the
bottom one, with the most functionality.
Maybe I'm just constrained by having worked in my problem domain (data
acquisition and processing) for so long. Could you give a simple
example?
jonathon wrote:
>>Real-world classes are orthonogal. Define them by multiply inheriting
>
>
>>from singly inheritant hierarchies dedicated to narrow functional
>>requirements. ie, Chop up the functionality you need into so many
>
> singly
>
>>inheritant class hierarchies, then define classes which inherit from
>>exactly one class from each singly inheritant class tree.
>
>
> I've been thinking about this, and I have a question.
>
> Does this mean the derived classes would only override methods rather
> than adding new ones?
Ideally, the derived class inherits one from column A, one from column
B, one from column C (old metaphor from ordering from a Chinese menu)
and, voila!, you have the class you want. But, yes, one might then
expect to override an inherited method or two.
Whether or not the derived, composite class defines its own methods
would vary. In the example I provide below, probably not, because the
superclasses exhaustively supply all the functionality desired. But what
we are doing in this scheme is treating the singly-inheritent class tree
as (what's the term?) abstract. Not strictly, because they can be useful
standalone. But in general, I am creating a workhorse,
application-specific class with which I intend to make my application
really happen. And it may well be that with these classes I will add
actual application semantics, so then, yeah, the new methods get
introduced.
> It doesn't *seem* to make sense to have the
> class tree getting 'wider' with each derived class.
I think of it as a separate application tree whose classes pick and
choose from useful singly-inheritant class "libraries", if you will. So
I am not extending those trees when I list one of their classes as a
superclass, I am adopting the functionality that superclass offers from
its narrow domain.
> Also, it *seems*
> the only derived class you would want from each tree would be the
> bottom one, with the most functionality.
Pretty much. But if I go crazy and make a highly specific "bottom"
class, its superclass is probably still useful to other clients.
>
> Maybe I'm just constrained by having worked in my problem domain (data
> acquisition and processing) for so long. Could you give a simple
> example?
In the GUIs I build, instantiable view elements inherit from trees
dedicated to, well, here are the root classes (and their domains):
Family (collection), Image (display output), Control (user input), and
Focus (current user input target).
kenny
--
Cells? Cello? Cells-Gtk?: http://www.common-lisp.net/project/cells/
Why Lisp? http://lisp.tech.coop/RtL%20Highlight%20Film
"Doctor, I wrestled with reality for forty years, and I am happy to
state that I finally won out over it." -- Elwood P. Dowd
··········@gmail.com writes:
>
>
> Hello Takuon,
>
> I've been in a similar situation. All we use at work is C++, as the
> end-all and be-all of design. And the next big project will be moving
> to C#.
>
> Question: how do you translate OOP to Lisp? For example, for
> delegates, inheritance, etc.? We have a number of components that
> share common functionality, and currently we do that with C++. How
> would Lisp do it?
Using CLOS, the built-in standard Common Lisp Object System.
Now, some of the OO techniques you are used to will not really be
needed, since one of the benefits of CLOS is that it has dynamic
multiple dispatch of methods. In other words, the effective method for
a "generic function" is chosen based on the type of ALL of the required
arguments.
The other major difference is that methods in CLOS do not belong to
classes, but rather to generic functions. This is actually a major win,
since it means that you can add new methods to existing generic
functions and write new generic functions for existing classes WITHOUT
having to change the original source code.
There are also a lot more features, but for initial usage, those two are
the most prominent, IMHO.
--
Thomas A. Russ, USC/Information Sciences Institute
I see I am not the only one in this situation then.
I turned to Lisp because my intuition seemed
to be telling my logical self that the "answer"
lay in an unexpected direction, a direction
that I had shut out of my conciousness long ago
because of its complicated looking parentheses
and reputation for being "difficult" while
all the while a massive campaign of persuasion
and hype continued to back C and C++.
In other, opposing camps, an equally steady
drumbeat of support rallies around Java or
Ruby or Python or C#.
I began to wonder if this ancient Lisp might not
offer some new perspective, some new insight
into the problem of shaping more efficaciously
the algorithm or task under development.
Instead I am in the process of discovering
much more,
an astonishing secret that has been in the
open all this time for those who are willing
to experiment and see, that, that the conceptions
of C++, touted as revolutionary by an unending
stream of supporters, are instead but the
mangled and hobbled disfigurements of ideas
for more cleanly and nobly expressed
in Lisp.
Tak
<··········@gmail.com> wrote in message
·····························@l41g2000cwc.googlegroups.com...
>
> Hello Takuon,
>
> I've been in a similar situation. All we use at work is C++, as the
> end-all and be-all of design. And the next big project will be moving
> to C#.
>
> Question: how do you translate OOP to Lisp? For example, for
> delegates, inheritance, etc.? We have a number of components that
> share common functionality, and currently we do that with C++. How
> would Lisp do it?
>
Takuon Soho wrote:
> I begin by tossing my beloved
> "The C++ Programming Language" by
> Stroustrup into the wastebasket.
Did you achieve this on the first try? Indeed, you mus6
be an expert C++ programmer. Welcome to the Lisp fraternity!
We need more programmers who can work from the 3-point line...