Inconsistencies in WeakSet implementation
Stéphane Rollandin
lecteur at zogotounga.net
Mon Jun 21 08:26:46 UTC 2004
Hello all,
while debugging an object of mine using weak sets, I found
inconsistencies in the WeakSet implementation which, when cleaned up,
solved my problem. Still, I don't get the full picture, so here is what
I kind of understood. I am sending an [ENH] in another message providing
my "fix" but it sure should be looked at carefully by someone who knows
what this is all about.
here we go:
empty slots in the array of a WeakSet are occupied by a flag (some
object) while they are nil in a Set.
it seems that nil values can still make their way inside a WeakSet
array, and this is why I got a bug in the first place. curiously, some
methods in WeakSet do handle nil values while other don't (expecting
flag always for an empty slot) and when I changed them the bug was gone.
the methods I found (and changed in my [ENH]) which do not handle nil are:
WeakSet>>fixCollisionsFrom:
WeakSet>>includes:
WeakSet>>like:
WeakSet>>remove:ifAbsent:
WeakSet>>scanFor:
in practice if a nil value appears in the array we get a walkback. this
is what happened to me (but I could not figure out how this happened)
now the following methods do handle nil values in the array:
WeakSet>>add:
WeakSet>>collect:
WeakSet>>do:
WeakSet>>do:after:
WeakSet>>growTo:
WeakSet>>slowSize:
there is no class comment in WeakSet, so I don't know why the flag is
required instead of nil. methods comments are the same as the ones in
the super class Set, so they are often at odd with the implementation
(see WeakSet>>scanFor: and WeakSet>>fixCollisionsFrom: for very
misleading comments talking about nil where the code only handles flag)
I don't know what this flag business is all about, but if it is indeed
necessary to keep both nil and flag has an empty slot specification,
then certainly the code snippet
(each _ array at: index) == nil or: [each == flag]
which is found all other the place could be refactored:
self hasEmptySlotAt: index
with
hasEmptySlotAt: index
^ (array at: index) isNil or: [(array at: index) == flag]
hopefully all of this make sense. please remember I just poke at the
code today because of a bug. I do not claim to have fully understood how
WeakSet is supposed to behave.
Stef
More information about the Squeak-dev
mailing list
|