stupid thread question

Michael Vanier mvanier at endor.bbb.caltech.edu
Tue Jun 13 20:59:47 EDT 2000


gmcm at hypernet.com (Gordon McMillan) writes:

> Michael Vanier: 
> 
> >I wrote a little python script using the thread module the other day.  I
> >wanted to be able to set a flag in the parent thread that would be read
> >in the child thread.  So I set a flag variable (an integer in this case)
> >in the parent, created the child thread, and then checked the value of
> >the flag every time through a loop in the child thread to see if it had
> >changed.  It turns out that the child thread apparently made a copy of
> >the flag, because when it changed in the parent it didn't change in the
> >child. 
> 
> >To fix this, I changed the flag to be a list with one integer element. 
> >Now, when I change the list element in the parent, the child sees it
> >too.  
> 
> 
> Let me guess. You did something like make "flag" a module level global, and 
> then did "from ... import *" in the other.

Even dumber than this; it was all in the same file.  I set the global in the
parent thread, and expected that the new thread would see the new value when
it was changed.

> 
> If you had referenced "module.flag", all would have worked. But that 
> stinks, too. Your thread should have a flag member, and the parent thread 
> should set it (through a setter, if you really want to be virtuous <wink>). 
> That way the flag becomes part of the thread's API, instead of a bass-
> ackwards dependency.
> 

Well, the thread wasn't an object; I just called a function and expected that
it would see the same data (see below).

> 
> > I gather that what this means is that there is a fundamental
> >distinction between atomic types like integers and reference types like
> >lists or dictionaries.  However, since python treats everything as a
> >reference this seems inconsistent to me.  So what I want to know is:
> >what is the cause of this behavior, and what is the justification for
> >it?  Or could it be a bug? 
> 
> Aahz is correct (as usual). It has to do with assignment and immutability. 
> To see assignment to any immutable (not in your global or local namespace), 
> you have to see the immutable through some larger context. Say, a module 
> namespace, or (as you did) through a container object.
> 
> - Gordon

So what you're saying is that a thread's namespace is not the same as the
global namespace of the parent.  This is puzzling, since that's what I
thought a thread was: effectively a new process which shares the parent's
namespace.  Is this in a FAQ somewhere?  Or am I just not getting it?

To further complicate things, here is a stripped-down version of the code
that actually works!

#! /usr/bin/env python

import os, thread

def thread_func():
    while 1:
        print "running child thread..."
        if stop:  
            print "child thread is done"
            break


stop = 0  
thread.start_new_thread(thread_func, ())
os.system("sleep 2")
stop = 1
print "parent thread is done"
os.system("sleep 2") # Wait for child thread to finish.
# end of test program

The original program has a Tk interface, which may account for the
difference.  Nevertheless, given what you've said, why does this work?

Mike


--------------------------------------------------------------
Mike Vanier	mvanier at bbb.caltech.edu
Department of Computation and Neural Systems, Caltech 216-76
GNU/Linux: We can't lose; we're on a mission from God.



More information about the Python-list mailing list