confused by bindings
Joshua Macy
l0819m0v0smfm001 at sneakemail.com
Thu Sep 20 18:19:17 EDT 2001
Doing self.count += 1 in the __init__ creates an instance variable. You
have to either refer to it by the explicit class variable name, e.g.
A.count, or you have to use a mutable type like a list and do e.g.
self.count[0]. Look at what's in the dictionaries:
>>> class A:
...
count = 0
...
def __init__(self):
...
self.count += 1
...
>>> a = A()
>>> b = A()
>>> dir(A)
['__doc__','__init__','__module__','count']
>>> A.count
0
>>> A.__dict__['count']
0
>>> dir(a)
['count']
>>> a.count
1
>>> a.__dict__['count']
1
>>> class B:
...
count = []
...
def __init__(self):
...
self.count[0] += 1
...
>>> c = B()
>>> d = B()
>>> dir(B)
['__doc__','__init__','__module__','count']
>>> B.count
[2]
>>> dir(c)
[]
Does that help any?
Joshua
Sam Falkner wrote:
> Here's what I've found. I tried four different methods, putting them
> into two modules: work and test. The four methods:
>
> (1) Borg class,
> (2) class variable, set as self.count,
> (3) class variable, set as Class.count, and
> (4) global-to-module variable.
>
> When I tried this, (1) and (2) failed, (3) and (4) worked. But, I
> went back and re-applied (3) and (4) to my existing application, and
> they still failed.
>
> I would have expected all four of these to work, except perhaps (2),
> which I would have expected either to work or to fail with a NameError
> or somesuch.
>
> Here are the two modules. My output is as follows:
>
> $ ./test.py -v
> testFour (test.WorkTestCase) ... ok
> testOne (test.WorkTestCase) ... FAIL
> testThree (test.WorkTestCase) ... ok
> testTwo (test.WorkTestCase) ... FAIL
>
> ======================================================================
> FAIL: testOne (test.WorkTestCase)
> ----------------------------------------------------------------------
> Traceback (most recent call last):
> File "./test.py", line 13, in testOne
> self.failUnlessEqual(len(junk), b.countone)
> File "/opt/etext/lib/python2.1/unittest.py", line 273, in failUnlessEqual
> raise self.failureException, (msg or '%s != %s' % (first, second))
> AssertionError: 5 != 1
> ======================================================================
> FAIL: testTwo (test.WorkTestCase)
> ----------------------------------------------------------------------
> Traceback (most recent call last):
> File "./test.py", line 19, in testTwo
> self.failUnlessEqual(len(junk), work.Two.count)
> File "/opt/etext/lib/python2.1/unittest.py", line 273, in failUnlessEqual
> raise self.failureException, (msg or '%s != %s' % (first, second))
> AssertionError: 5 != 0
> ----------------------------------------------------------------------
> Ran 4 tests in 0.003s
>
> FAILED (failures=2)
>
> Note that I still can't get *anything* to work in my real application.
>
> Can anyone explain what's going on? Or, if this was discussed a month
> or so ago, can someone tell me the subject line, so I can look it up
> on google?
>
> Thanks!
>
> - Sam
>
> #! /usr/bin/env python
>
> # work.py module
>
> class Borg:
> __shared_state = {}
> def __init__(self):
> self.__dict__ = self.__shared_state
> self.countone = 0
>
> class One:
> def __init__(self):
> borg = Borg()
> borg.countone += 1
>
> class Two:
> count = 0
> def __init__(self):
> self.count += 1
>
> class Three:
> count = 0
> def __init__(self):
> Three.count += 1
>
> fourcount = 0
>
> class Four:
> def __init__(self):
> global fourcount
> fourcount += 1
>
> def work1():
> junk = []
> for i in range(5):
> junk.append(One())
> return junk
>
> def work2():
> junk = []
> for i in range(5):
> junk.append(Two())
> return junk
>
> def work3():
> junk = []
> for i in range(5):
> junk.append(Three())
> return junk
>
> def work4():
> junk = []
> for i in range(5):
> junk.append(Four())
> return junk
>
> #! /usr/bin/env python
>
> # test.py module
>
> import unittest
>
> import work
>
> class WorkTestCase(unittest.TestCase):
> def testOne(self):
> b = work.Borg()
> b.countone = 0
> junk = work.work1()
> self.failUnlessEqual(len(junk), b.countone)
>
> def testTwo(self):
> work.Two.count = 0
> junk = work.work2()
> self.failUnlessEqual(len(junk), work.Two.count)
>
> def testThree(self):
> work.Three.count = 0
> junk = work.work3()
> self.failUnlessEqual(len(junk), work.Three.count)
>
> def testFour(self):
> work.fourcount = 0
> junk = work.work4()
> self.failUnlessEqual(len(junk), work.fourcount)
>
> def buildall():
> return unittest.makeSuite(WorkTestCase, 'test')
>
> if __name__ == '__main__':
> unittest.main('test', 'buildall')
>
More information about the Python-list
mailing list