65
67
self.assertTrue(obj not in container,
66
68
'We found %s in %s' % (obj, container))
70
def assertFillState(self, used, fill, mask, obj):
71
self.assertEqual((used, fill, mask), (obj.used, obj.fill, obj.mask))
73
def assertRefcount(self, count, obj):
74
"""Assert that the refcount for obj is what we expect.
76
Note that this automatically adjusts for the fact that calling
77
assertRefcount actually creates a new pointer, as does calling
78
sys.getrefcount. So pass the expected value *before* the call.
80
# I don't understand why it is count+3 here, but it seems to be
81
# correct. If I check in the calling function, with:
82
# self.assertEqual(count+1, sys.getrefcount(obj))
83
# Then it works fine. Something about passing it to assertRefcount is
84
# actually double-incrementing (and decrementing) the refcount
85
self.assertEqual(count+3, sys.getrefcount(obj))
68
87
def test_initial(self):
69
88
obj = _module.StaticTupleInterner()
70
89
self.assertEqual(0, len(obj))
71
90
st = StaticTuple('foo', 'bar')
72
self.assertEqual(0, obj.used)
73
self.assertEqual(0, obj.fill)
74
self.assertEqual(0x3ff, obj.mask) # 1024 - 1
91
self.assertFillState(0, 0, 0x3ff, obj)
76
93
def test__lookup(self):
77
94
# The tuple hash function is rather good at entropy. For all integers
142
159
self.assertIn(k2, obj)
143
160
self.assertIn(k3, obj)
144
161
self.assertNotIn(k4, obj)
164
obj = _module.StaticTupleInterner()
165
self.assertFillState(0, 0, 0x3ff, obj)
166
k1 = StaticTuple('foo')
167
self.assertRefcount(1, k1)
168
self.assertIs(k1, obj.add(k1))
169
self.assertFillState(1, 1, 0x3ff, obj)
170
self.assertRefcount(2, k1)
172
self.assertRefcount(3, k1)
173
self.assertIs(k1, ktest)
175
self.assertRefcount(2, k1)
176
k2 = StaticTuple('foo')
177
self.assertRefcount(1, k2)
178
self.assertIsNot(k1, k2)
179
# doesn't add anything, so the counters shouldn't be adjusted
180
self.assertIs(k1, obj.add(k2))
181
self.assertFillState(1, 1, 0x3ff, obj)
182
self.assertRefcount(2, k1) # not changed
183
self.assertRefcount(1, k2) # not incremented
184
self.assertIs(k1, obj[k1])
185
self.assertIs(k1, obj[k2])
186
self.assertRefcount(2, k1)
187
self.assertRefcount(1, k2)
188
# Deleting an entry should remove the fill, but not the used
190
self.assertFillState(0, 1, 0x3ff, obj)
191
self.assertRefcount(1, k1)
192
k3 = StaticTuple('bar')
193
self.assertRefcount(1, k3)
194
self.assertIs(k3, obj.add(k3))
195
self.assertFillState(1, 2, 0x3ff, obj)
196
self.assertRefcount(2, k3)
197
self.assertIs(k2, obj.add(k2))
198
self.assertFillState(2, 2, 0x3ff, obj)
199
self.assertRefcount(1, k1)
200
self.assertRefcount(2, k2)
201
self.assertRefcount(2, k3)
203
def test_discard(self):
204
obj = _module.StaticTupleInterner()
205
k1 = StaticTuple('foo')
206
k2 = StaticTuple('foo')
207
k3 = StaticTuple('bar')
208
self.assertRefcount(1, k1)
209
self.assertRefcount(1, k2)
210
self.assertRefcount(1, k3)
212
self.assertRefcount(2, k1)
213
self.assertEqual(0, obj.discard(k3))
214
self.assertRefcount(1, k3)
216
self.assertRefcount(2, k3)
217
self.assertEqual(1, obj.discard(k3))
218
self.assertRefcount(1, k3)
220
def test__delitem__(self):
221
obj = _module.StaticTupleInterner()
222
k1 = StaticTuple('foo')
223
k2 = StaticTuple('foo')
224
k3 = StaticTuple('bar')
225
self.assertRefcount(1, k1)
226
self.assertRefcount(1, k2)
227
self.assertRefcount(1, k3)
229
self.assertRefcount(2, k1)
230
self.assertRaises(KeyError, obj.__delitem__, k3)
231
self.assertRefcount(1, k3)
233
self.assertRefcount(2, k3)
235
self.assertRefcount(1, k3)