This is the mail archive of the guile@sourceware.cygnus.com mailing list for the Guile project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

Re: Some questions about GOOPS and CLOS in general


Jost Boekemeier <jostobfe@calvados.zrz.TU-Berlin.DE> writes:

> > In any OO paradigm I've worked with, methods return values without
> > problems.
> 
> Yes.  These classes are "factory" classes.  They simply return
> a new object. 

This is very narrow view... and also quite wrong. A class with a
method that happens to return a container object is not necessarily a
factory.

Matrices are in fact container objects.

> Then CLOS and GOOPS are broken. :) In CLOS how can you protect a slot
> from beeing changed by a foreign method?  You cannot since in CLOS
> methods do not belong to an object.

Same way you protect anything from being changed by anything else: by
encapsulating it into a module.

Encapsulation and OO are separate issues.

> This means that they can operate on the whole set of objects that
> populate your system causing unwanted side effects.

See above.

The advantage of CLOS approach is that it does not forbid *wanted*
side effects.

> > The problem is that this introduces redundancy. The function "knows"
> > which other functions it calls. But the module doesn't know
> > that. Therefore you have to type the same information twice: function
> > f calls function g, and therefore you have to tell the current module
> > F to import a function from module G.
> 
> True.  But it wasn't me who decided to use scheme as the base
> for the GNU extension language. :)

Care to mention any working module system whose imports are all
implicit? My point was that the whole purpose of the module system is
that you *have* to import features you need, regardless of whether you
want to call them, reference them, inherit them or turn them into a
little fluffy toy dog.

> > On another line, one of the basic assumptions of CLOS is that
> > encapsulation is orthogonal to OO - in other words, Java
> > implementation of modules as singletons is Java's design choice rather
> > than obvious thing to do in any OO system.
> 
> Java and other good OO implementations don't have modules at all.
> In Java and Eiffel a module /is a/ class.  And a package is just
> a set of modules (module == class).

I am saying that this is just one particular way to design a
system. It's not the only one and it's by no means the *right* one -
class-grain encapsulation leads to either proliferation of trivial
methods or 'friend' abomination from C++.

BTW, this is just a rehash of an old discussion on comp.lang.list
(check DejaNews) - the whole point is that with class = module, you
can prevent yourself from introducing unwanted side effects, but you
can not allow yourself to introduce wanted side effects.

> > For example, it's a really good idea to program all the matrix classes
> > in one module - direct access to slots,
> 
> I think when you say "module" you really mean the package concept.
> If I understood Mikael correctly there is exactly one class per module.

Either you misunderstand Mikael or this should be corrected.

Modules are unrelated to classes.

Except in bondage & discipline OO languages.

> When you want to put more than one class into a module, how do you
> export accessor X for class a and accessor X for class b?

You export generic function X.

> > Precisely - so why do you insist on encapsulating classes?
> 
> class piano has slot pedal
> class bike  has slot pedal
> 
> class s inherits from piano and bike. 
> You must not merge these two slots.

Well, how would you do it in Java?

s.pedal() would be equally bad idea.

Unless, of course, you use the module system to rename one of the
pedals on import. Note that putting the two classes with equally named
slots in the same module would be noticed by the module system.

> > > But he treats modules just like classes and I quite like the trick.
> > > Normaly a module /owns/ one or more classes.  In his system a module
> > > /is a/ class.
> > 
> > Class in GOOPS is a type.
> 
> Yes, but why do you say that?

Let's see. Class (by definition) is set of values. Type (by
definition) is set of values. The conclusion follows from the fact
that 'defining is' relation is equivalence relation.

While you may argue that class is actually bunch of methods that
manipulate it, it's just one specific view of a type. The fact that
it's also quite narrow is responsible for the general suckiness of the
most popular OO systems.

> The problem with goops is that an object doesn't protect its slots.
> So the module has to handle this.

The module is supposed to handle this. What's your point?

> > Even if fc1 is a lambda, this is misleading. It is also vastly
> > inferior to any OO with multiple dispatch (see below).
> 
> May be.  But multiple dispatch has the problem that the methods
> do neither belong nor are they  associated with the object they
> manipulate.

Well, so far you consistently fail to prove that this is a problem.

If I understand you correctly, you're saying that this is a problem
because modules have to handle protection work. This is false argument
because protection is what modules are supposed to do, and because any
protection is supposed to be handled by modules.

> > To repeat: while this is true, this method can't give you polymorphism
> > of the sort (m1 format binary-formatter) vs (m1 format text-formatter)
> 
> I don't understand.  Depending on the type of m1 format is either
> binary-formatter or text-formatter.  

Nope.

(define m1 17)
(define formatter text-formatter)
(format m1 formatter) => "17"
(define formatter binary-formatter)
(format m1 formatter) => "\001\000\000\000\021"
			  ^^^^ number tag
			      ^^^^^^^^^^^^^^^^number
(format "blah" formatter) => "\000\000\000\000\004blah"
			      ^^^^ tag
			          ^^^^^^^^^^^^^^^^length
						  ^^^^ contents
(format "blah" text-formatter) => "\"blah\""

Etc. This is just a simplest example. You could just as easily have a
bunch of XML tag representations with inheritance and format them for
plaintext streams, LaTeX stream or HTML stream.

> > How about (get-nth list 5) ?
> 
> I assume get-nth is an object of the class <get-nth> and list
> is the method selector.

No, list is an object, get-nth is a virtual slot (that represents list
contents) and 5 is the additional parameter needed for a proper slot
access.

I don't see why getters/setters wouldn't accept additional parameters.

Also, in Scheme, commands should be self-explanatory by their English
name.

(color fruit red)

is meaningless in the above sense.

(set-color! fruit red)

is not.

Or are you suggesting to drop Schemishness in order to implement
module and object system?

> > (generic-set! (get-nth list 5) 15)
> 
> What does that do?  As I understand scheme you cannot set! a list 
> to something.

Check setf in Common LISP and reread discussion on generic set on this
list. It's a macro that converts getter to setter for any
getter/setter pair.

(from Common LISP):

(setf (car foo) 1) => (setcar foo 1)
(setf (color object) red) => (setcolor object red)
(setf (aref vector 16) 6) => (aset vector 16 6)

-- 
How to eff the ineffable?

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]