Abstract factory was [self-interest] patterns and Self

Albertina Lourenci lourenci at lsi.usp.br
Thu Dec 14 19:31:38 UTC 2000

Jecel Assumpcao Jr wrote:

> As promissed, here are some quick comments from a Self programmer's
> viewpoint on the patterns in the "Design Patterns" book by Erich Gamma,
> Richard Helm, Ralph Johnson and John Vlissides. The numbers in
> parenthesis are the page numbers where each pattern is described.
> I hope this helps,
> -- Jecel

I do thank you for your efforts, although I will not be able to examine
all the GOF's D.P. for the time being. It is adding a special flavour
to my reading of Peter Wegner's paper.
But let's examine the Abstract Factory.

I immediately realized   it could be used to achieve portability across
different systenms. Well, indeed GOF states that Et++  (paper  46-57)
OOPSLA 88 uses the Abstract Factory pattern to achieve
portability across different Window Systems (X windows and Sun View)
page 95f in Known uses GOF's book.

So delegation is a powerful abstraction mechanism. There are various
viewpoints on what precisely makes a system "open"
One of the requirements is:
Interoperability. Open systems typically run on heterogeneous
hardware and software platforms. Platform differences should
be encapsulated in the system architecture to ease integration.

There are different versions of Self (???) for Macintosh, Sun,
now for Linux and later for Windows and so on...
Why not to build a  unique software architecture (? framework?)
to cope with this requirement?

What are the difficulties involved? What role  does Abstract Factory
play here? Can delegation alone do the same? I mean is it as
expressive the Abstract Factory pattern?
Hope I have expressed my impressions in correct technical terms.
If not please help me to clarify my reasoning.


> Creational Patterns
> --------------
> ===> Abstract Factory(87):
> I have suggested that it might be interesting to add abstract types to
> Self in the form of interface (to use Java terms) objects. This would
> be a good use of this pattern. Instead of writing
>                a: list copyRemoveAll
> which refers to a specific prototype (list) directly, we could have
>               a: interfaces sequence getOneFor: 'fifo'
> Of course, with dynamic types this pattern is considerably simpler in
> Self than in the book. I can't think of an example where this is used
> in Self 4.1.2.
> ===> Builder(97):
> This goes against the idea of creating new objects by simply cloning an
> existing one. Of course, sometimes cloning is anything but simple. See
> the copy method for morphs, for example. But it is probably better to
> stick with the current Self style of stuffing all the complexity in the
> 'copy' method instead of creating separate "builder" objects.
> ===> Factory Method(107):
> It is hard to see what the fuss is all about when you have dynamic
> types and cloning. Just put a prototype of the "concreteProduct" in a
> slot in the prototype of the "concreteCreator" and patch the copy
> method to go down one level, here. See the low level graphical
> framework in Self (canvas, windows, graphics contexts...) for an
> example. No big deal.
> ===> Prototype(117):
> This *is* a prototype based language. You can't avoid using this
> pattern if you want to! No big deal.
> ===> Singleton(127):
> All objects in Self are singleton unless they have traits clonable (or
> some suitable replacement) as one of their ancestors. No big deal.
> Structural Patterns
> --------------
> ===> Adaptor(139):
> This is *so* much simpler with implicit, dynamic delegation (data
> parents). When wrapping an objects with many methods, you only have to
> worry about the ones you will need to change, not about all of them.
> And Self really makes this pattern more powerful by allowing you to
> override data slots as well as method slots (even better: you can
> override a data slot with a method slot and vice versa). The only thing
> to watch out is how to handle copying and how to avoid having the
> adapted object's identity "leak out". Reflection might help with these
> problems. I don't know of any examples in Self 4.1.2.
> ===> Bridge(151):
> You could use implicit delegation for this pattern, but the example in
> Self (canvas) uses explicit delegation instead.
> ===> Composite(163):
> Morphs are a great example of this. I am not sure that any Self
> features help very much, here, other than having dynamic typing make
> what objects can be plugged into what others more flexible.
> ===> Decorator(175):
> It would be more pleasing, in my opinion, to use data parents (implicit
> delegation) for this pattern. I don't know of any examples where it is
> used in Self 4.1.2.
> ===> Facade(185):
> I don't think Self makes this pattern simpler than in other languages.
> I was going to say that 'desktop' could be an example of this, but that
> is pushing it a little....
> ===> Flyweight(195):
> I would say that Self's advanced inlining compiler technology makes
> this pattern less necessary than in other systems. This pattern is also
> used as a classic example of the advantages of reflective systems (see
> the Open Implementation pages).
> http://www.parc.xerox.com/spl/projects/oi/workshop-94/foil/main.html
> Oddly enough, there are examples of this in Morphic. There are several
> cases where the strategy pattern should have been used but the
> information was represented as simple integers instead (see alignLeft,
> alignCenter and alignRight in columnMorph and similar options in
> related morphs). This is a design bug - I think the flyweight pattern
> should never be used in Self.
> ===> Proxy(207):
> Exactly the same comment as for Adaptor. Except that there are plenty
> example of this in objects named, oddly enough, "proxies".
> Behavioral Patterns
> ---------------
> ===> Chain of Responsibility(223):
> The event handling in the user interface partly uses this pattern.
> Having implicit delegation might be nice, but I am not sure it would
> make much of a difference, here.
> ===> Command(233):
> Event objects in the user interface could be considered an example of
> this. I think that this is nicer to do in Self since making lots of
> objects that are a little different isn't as bad as when you have to
> create a different class for each one.
> ===> Interpreter(243):
> The only example that comes to mind is tinySelf 1. While the Self
> language itself doesn't make this pattern much simpler, being able to
> develop and interpreter in a dynamic user environment really helps. I
> think that most cases where this pattern might be used could be better
> implemented as a parser generated by Mango instead.
> ===> Iterator(257):
> As Smalltalk Stream classes show, this pattern is much easier to
> implement in dynamically typed languages. I don't know of any examples
> in Self 4.1.2 and sometimes miss them a lot. My students implemented
> iterators for matrix objects (for an unfinished 3D GUI project) and
> that made a lot of the higher level code considerably simpler.
> Iterators are important in languages like Self and Smalltalk that have
> a very awkward syntax for accessing vector elements.
> ===> Mediator(273):
> Hmmm... I am not sure, but the damage/redraw logic distributed between
> morphs and the worldMorph might be considered an example of this. I
> don't see that Self is particularly helpful in this case.
> ===> Memento(283):
> Don't you just pity the poor slobs who have to program with systems
> that can't save Snapshots?  :-)
> You don't need this pattern with Snapshots, but in Self we do have it
> in the form of the Transporter. It would be nice to replace these two
> great tools with a real persistent object store.
> ===> Observer(293):
> I would say that the damage/redraw code also includes an example of
> this pattern. Self doesn't help with this either, but a reflective
> layer might.
> ===> State(305):
> Who needs this when you can have data parents? See the various tree
> objects in Self 4.1.2 as an example of why we can live without this (or
> as an example of how to implement this with implicit delegation,
> depending on your viewpoint).
> ===> Strategy(315):
> This can also be implemented as data parents, but I have used explicit
> delegation in my own programs instead. In the latter case Self doesn't
> bring much to the party.
> ===> Template Method(325):
> This is used in many places in Self, including in the C++
> implementation of the virtual machine. For some reason I tend to think
> of the Beta language when I look at this pattern, but it is easy in
> Self as well.
> ===> Visitor(331):
> I can't think of any examples of this in Self, though some of the
> runtime code generated by Mango might qualify.

| Albertina Lourenci                                       |
| PhD  in Architecture and Urbanism                        |
| post-doctorate researcher                                |
| Laboratory of Integrated Systems University of Sao Paulo |
| Avenida Professor Luciano Gualberto, 158 Travessa 3      |
| CEP: 05508-900                                           |
| Sao Paulo Sao Paulo State Brazil                         |
| Voice: +55 011 818 5254                                  |
| Fax: +55 11 211 4574                                     |

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.selflanguage.org/pipermail/self-interest/attachments/20001214/ebe29b61/attachment.html>

More information about the Self-interest mailing list