Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

instance references?

0 views
Skip to first unread message

bytecolor

unread,
Jan 29, 2006, 6:20:18 PM1/29/06
to
I'm working on a simple graphics package. I've got a function show()
that the user needs to call at the end of the script to actually
display the points, lines and circles that have been defined in the
script.

p1 = point(0, 0)
l1 = line(1, 3, -4, 5)
c1 = circle(-2, 3, 1)
show()

In each __init__() method of the point, line, and circle objects I add
self to a list in a separate module, then show() uses this list to
actually draw the objects. This works except:

l1 = line(point(1, 3), point(-4, 5))
c1 = circle(point(-2, 3), 1)

adds the references to the points used to define the objects to the
render list. I only want objects that have been assigned to a variable
to be rendered. (Try to ignore the function overloading.)

So how can I tell if an instance of point, line or circle has actually
been assigned to a variable?

--
bytecolor

Alex Martelli

unread,
Jan 29, 2006, 7:03:12 PM1/29/06
to
bytecolor <byte...@yahoo.com> wrote:
...

> So how can I tell if an instance of point, line or circle has actually
> been assigned to a variable?

You can't really distinguish whether an object has been assigned to a
variable, an item in a list, an attribute, etc etc -- all of these
assignments are much the same thing, there is nothing special about
variables to distinguish them from the other kind of 'labels'. Indeed,
for example, global variables are EXACTLY the same thing as attributes
of a module objects which in turn are exactly the same things as values
in the module's __dict__ -- so, any hopes of distinguishing between
variables, attributes, and items inside a container, must clearly be
abandoned.

You can do various other things that might come close to what you want,
such as using weak references in your list (if no 'true' reference
exists, an object goes away and _weak_ references to that object let you
check if the object is still around or has gone away) -- that will let
you know whether the object has been assigned to *anything* (you can
perform a similar task by checking on the number of references extant to
an object). But checking if the existing references are indeed
'variables' or something else is a hard, unrewarding task.


Alex

bytecolor

unread,
Jan 29, 2006, 8:30:38 PM1/29/06
to
Thanks Alex, the weak references *seem* to be doing what I want for
now.

In each __init__() I use:
aptbase.drawables.append(weakref.ref(self))

Then in show():
for d in aptbase.drawables:
o = d()
if o is not None:
# render it

--
bytecolor

Alex Martelli

unread,
Jan 29, 2006, 11:44:56 PM1/29/06
to
bytecolor <byte...@yahoo.com> wrote:

Looks good, so apparently you didn't particularly care about assignment
to variables vs assignment to other "labels" -- great!

My favourite way to use weakref is slightly different: I would have

aptbase.drawables = weakref.WeakValueDictionary

then in each __init__

aptbase.drawables[len(aptbase.drawables)] = self

then in show:

for o in aptbase.drawables.values():
# render it


Not a vastly different idiom from yours, mind you, but I like not having
to check whether an object has gone away -- a WeakValueDictionary's
entries just disappear when the value object goes away, so that at any
time looping on its .values() is safe as brick houses!-)


Alex

Scott David Daniels

unread,
Jan 30, 2006, 4:15:43 PM1/30/06
to
Alex Martelli wrote:
> My favourite way to use weakref is slightly different: I would have
> aptbase.drawables = weakref.WeakValueDictionary
typo here:
aptbase.drawables = weakref.WeakValueDictionary()

> then in each __init__
> aptbase.drawables[len(aptbase.drawables)] = self
> then in show:
> for o in aptbase.drawables.values():
> # render it
The keys you are choosing are probably not a good idea.
Problem demo:

a,b,c = Something(), Something(), Something()
b = None
d = Something() # overwrites the d entry.

I'd use:
aptbase.drawables[id(self)] = self

--
-Scott David Daniels
scott....@acm.org

Alex Martelli

unread,
Jan 30, 2006, 9:58:11 PM1/30/06
to

Good point -- the id isn't going to be reused until self is gone, of
course. I normally use a monotonically increasing counter (global or in
self's class), but there's no real reason for that -- id is simpler (and
using len as I had is definitely bugprone, as you mention).


Alex

Scott David Daniels

unread,
Jan 31, 2006, 7:37:46 PM1/31/06
to
Scott David Daniels wrote:
> Alex Martelli wrote: (in effect)

>> aptbase.drawables = weakref.WeakValueDictionary()
>> then in each __init__
>> aptbase.drawables[len(aptbase.drawables)] = self
>> then in show:
>> for o in aptbase.drawables.values():
>> # render it
>
> The keys you are choosing are probably not a good idea.
> Problem demo:
> a,b,c = Something(), Something(), Something()
> b = None
> d = Something() # overwrites the d entry.

In a tiny demo of what exactly the problem is, I managed to
mess up the comment.
a, b, c = Something(), Something(), Something()
b = None
d = Something() # overwrites the _c_ entry.

Silly me.

--Scott David Daniels
scott....@acm.org

0 new messages