[Q][Newbie] disappearing dependents?

Boris Gaertner Boris.Gaertner at gmx.net
Fri Nov 14 16:15:18 UTC 2003


willem van den ende <squeak at willemvandenende.com> wrote

<snip>
> The frustrating thing is: it
> works _sometimes_ - I must be making a silly mistake somewhere. It
especially
> stops working after I save the image.
>
> http://www.willemvandenende.com/RssClient.st
>
>I put the index.rss file I used in the unit tests here:
>
> http://www.willemvandenende.com/index.rss
</snip>

Willem, you are right, you loose a dependence. This is of course a mistake,
but it is not a silly mistake, but one that I saw never before. I recommend
this example to all those that are really interested in the MVC metaphor
(I hope you will kindly allow that those interested can download your
example.)

Now the problem itself:

In RssViewer>>open you write (among other things)

 model addDependent: self.

This puts your instance of  RssViewer into the collection of
dependents of the model instance that is referenced by the temporary
variable model.
The dependents are kept in an instance of DependentsArray and that is
a *week* subclass of Array. Week collections are magic at work: They
keep an element for as long as at least one non-weak reference to the
element exists. Elements that are not strongly referenced from elsewhere
are "automagically" garbage collected.

Your mistake is that you do not store the instance of RssViewer elsewhere
and therefore it is garbage collected at a moment that you cannot foresee,
but certainly when you save the image.

What can you do:
You have different options.
1. You can establish a strong reference to the instance of RssViewer.
That is simple, make it the model of  the top window (add the line that
I put between arrows):

 window _ (SystemWindow labelled: 'RSS viewer')
   -> model: self;  <-
    addMorph: titlesMorph

This removes the problem, but looks like a hack and it is one.
We use RssViewer as a model and are successful because a
SystemWindow does not require a lot of support from its
model.

2. You may conclude, that RssModel should not keep its dependents in
a weak collection. Again a bit of magic is sufficient to force RssModel
to store its dependents in an Array. You add the instance method

addDependent: anObject
 "Make the given object one of the receiver's dependents."

 |  deps  |
 deps _ self dependents.
 (deps includes: anObject) ifFalse:
  [self myDependents: (deps copyWith: anObject)].
 ^ anObject

Compare this with Object>>addDependent: to see that
a call copyWithDependent: was replaced with a call of
copyWith:  I think this is what we had in earlier versions
of Model (in Squeak 2.7 for example), before we changed
to weak arrays.


These are two ways to fix the problem. I think (and hope!)
that some subscribers will find time to tell us something about
the correct use of weak collections. I think you programmed against
a pattern that is implicitly introduced when we use weak collections
but we should make the rules explicit. (I feel that this is more
difficult and that I need more time to write down the rules. Perhaps
others will contribute their insights)

Greetings,
Boris





More information about the Squeak-dev mailing list