cannot find object instance

J

jimgardener

hi,
i am a python newbie..while trying out some message passing between
two object instances i came across a problem
moduleA.py
--------------------
import moduleB
class MyClassA:
def __init__(self):
self.age=0
self.address=''
def createClassB(self):
self.objB=moduleB.MyClassB()
def validate(self,age,address):
if(age >= 100 or address==''):
self.age=20;
self.address="Broadway,NewYork"
self.objB.display(self.age,self.address)
def callB(self):
self.objB.execute()

if __name__ == "__main__":
objA=MyClassA()
objA.createClassB()
objA.callB()

moduleB.py
------------------
import moduleA

class MyClassB:
def __init__(self):
self.createA()
def createA(self):
self.objA=moduleA.MyClassA()
def execute(self):
self.objA.validate(111,'')
def display(self,age,address):
print 'displaying:',str(age),address

when i run the code i get a message
AttributeError: MyClassA instance has no attribute 'objB'

Do i have to put a placeholder for objB in __init__ of MyClassA ?
is that why i get this error?someone please tell me how i can solve
this? I tried to put self.objB=None but it didn't work..(i was
thinking of java style objB=NULL )

please help
thanks
jim
 
B

Bruno Desthuilliers

jimgardener a écrit :
hi,
i am a python newbie..

From what I can see from your code, you're a newbie to programming in
general...
while trying out some message passing between
two object instances i came across a problem

First point : you have both a circular dependency between ModuleA and
ModuleB - which is better to avoid unless you really like headaches...
You mention Java somewhere else, so I assume you have some at least some
Java background. Point here is that Python is not Java, and doesn't
restrict you to one ("public") class per module. IOW, if you have two
strongly related classes (which is obviously the case here), better to
put both in a same module.
moduleA.py
--------------------
import moduleB
class MyClassA:
def __init__(self):
self.age=0
self.address=''
def createClassB(self):
self.objB=moduleB.MyClassB()

Why is this in a distinct method instead of being in the initializer ?
And why is it named create*Class* when it creates an *instance* ?
def validate(self,age,address):
if(age >= 100 or address==''):
self.age=20;
self.address="Broadway,NewYork"
self.objB.display(self.age,self.address)
def callB(self):
self.objB.execute()

Looks like a somewhat messy, circonvoluted and arbitrary
overcomplexificated control flow...
if __name__ == "__main__":
objA=MyClassA()
objA.createClassB()
objA.callB()

moduleB.py
------------------
import moduleA

class MyClassB:
def __init__(self):
self.createA()
def createA(self):
self.objA=moduleA.MyClassA()

You do understand that self.objA won't be the same MyClassA instance as
the one that instanciated this instance of MyClassB, do you ?
def execute(self):
self.objA.validate(111,'')
def display(self,age,address):
print 'displaying:',str(age),address

You don't have to call str on age here.
when i run the code i get a message
AttributeError: MyClassA instance has no attribute 'objB'

Indeed.

You first create an instance of MyClassA named objA, call createClassB()
on it which create an instance of MyClassB referenced by objA.objB.

When objA.objB is created, it itself creates another instance of
MyClassA referenced by objA.objB.objA, which is totally distinct from
objA...

Then you call objA.callB(),
which itself call objA.objB.execute(),
which in turn call objA.objB.objA.validate(),
which in turn call objA.objB.objA.objB.display().

But at this point, objA.objB.objA (which, I repeat, is *not* objA) has
no attribute objB since you didn't call objA.objB.objA.createClassB()...

You could have understood this by yourself, either the way I did
(mentally tracing program execution) or using a couple print statements
in your code (to effectively trace program execution), or using the
debugger...
Do i have to put a placeholder for objB in __init__ of MyClassA ?
is that why i get this error?someone please tell me how i can solve
this? I tried to put self.objB=None but it didn't work..

<ot>
Trying anything that comes to mind instead of trying to understand how
things work is a well-known antipattern named "programming by accident".
The best you can hope from this approach is that, for unknown reasons,
things accidentally seem to work. Until the day where, for still unknown
reasons, they either stop working, or it appears they never really
worked at all.

Needless to say, this approach is a pure waste of time.
</ot>

class ClassA(object):
def __init__(self, age=0, address=''):
self.age = age
self.address = address
self.b= ClassB(self)

def validate(self,age,address):
if(age >= 100 or address==''):
self.age=20;
self.address="Broadway,NewYork"
self.b.display(self.age, self.address)

def call_b(self):
self.b.execute()

class ClassB(object):
def __init__(self, a):
self.a = a
def execute(self):
self.a.validate(111,'')
def display(self, age, address):
print 'displaying: %s %s' % (age, address)

if __name__ == "__main__":
objA=ClassA()
objA.call_b()


Note that this is still uselessly messy and arbitrary
overcomplificated... Such a ping-pong between two classes is more often
than not a design smell.

HTH
 
M

Marc 'BlackJack' Rintsch

moduleA.py
--------------------
import moduleB

[…]

moduleB.py

Don't do that. Circular imports are a code smell. If two modules are
coupled that tight it's usually a sign that you want just one module or
factoring out something into a third module that is imported by both old
modules.

Ciao,
Marc 'BlackJack' Rintsch
 
J

jimgardener

On Aug 28, 9:35 pm, Bruno Desthuilliers <bruno.
(e-mail address removed)> wrote:
Such a ping-pong between two classes is more often
than not a design smell.


thanks Bruno,i understand my mistake..should have figured it out
myself
thanks again
jim
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,995
Messages
2,570,230
Members
46,817
Latest member
DicWeils

Latest Threads

Top