@@ -278,30 +278,67 @@ def test_set_next_entry(self):
278278
279279
280280class FrozenSetWriterTests (unittest .TestCase ):
281- def create_writer (self ):
281+ PySet_MINSIZE = _testcapi .PySet_MINSIZE
282+
283+ def create_writer (self , size = 0 ):
282284 # Test PyFrozenSetWriter_Create()
283- return _testcapi .PyFrozenSetWriter ()
285+ return _testcapi .PyFrozenSetWriter (size )
286+
287+ def compute_table_size (self , size ):
288+ table_size = self .PySet_MINSIZE
289+ while table_size <= size :
290+ table_size <<= 1
291+ return table_size
284292
285293 def frozenset_equal (self , result , expected ):
286294 if not isinstance (expected , frozenset ):
287295 expected = frozenset (expected )
288296 self .assertEqual (result , expected )
289297 self .assertEqual (type (result ), frozenset )
290298
299+ def test_get_table_set (self ):
300+ # Test size parameter of PyFrozenSetWriter_Create()
301+ PySet_MINSIZE = self .PySet_MINSIZE
302+
303+ def check_table_size (size , table_size ):
304+ writer = self .create_writer (size )
305+ self .assertEqual (writer .get_table_size (), table_size )
306+
307+ check_table_size (0 , PySet_MINSIZE )
308+ check_table_size (PySet_MINSIZE - 1 , PySet_MINSIZE )
309+ check_table_size (PySet_MINSIZE , PySet_MINSIZE * 2 )
310+ check_table_size (2 ** 15 - 1 , 2 ** 15 )
311+
312+ def create_items (self , nitem ):
313+ # Use mortal (and unique) objects to be able to detect reference leaks
314+ return tuple (object () for _ in range (nitem ))
315+
291316 def test_append (self ):
292317 # Test PyFrozenSetWriter_Append()
293- items = (1 , 2 , 3 )
294- writer = self .create_writer ()
295- for item in items :
296- writer .add (item )
297- self .frozenset_equal (writer .finish (), items )
318+ items = self .create_items (self .PySet_MINSIZE * 2 - 1 )
319+ table_size = self .compute_table_size (len (items ))
320+ for prealloc in (0 , len (items ) // 2 , len (items ), len (items ) * 10 ):
321+ with self .subTest (size = prealloc ):
322+ writer = self .create_writer ()
323+ for item in items :
324+ writer .add (item )
325+ self .frozenset_equal (writer .finish (), items )
298326
299327 def test_update (self ):
300328 # Test PyFrozenSetWriter_Update()
301- writer = self .create_writer ()
302- writer .update ((2 , 5 ))
303- writer .update ((5 , 7 ))
304- self .frozenset_equal (writer .finish (), {2 , 5 , 7 })
329+ items1 = self .create_items (self .PySet_MINSIZE - 1 )
330+ items2 = self .create_items (self .PySet_MINSIZE - 1 )
331+ common = self .create_items (self .PySet_MINSIZE - 1 )
332+ expected = set (items1 ) | set (items2 ) | set (common )
333+ total = len (expected )
334+ self .assertEqual (total , len (items1 ) + len (items2 ) + len (common ))
335+
336+ for prealloc in (0 , total // 2 , total , total * 10 ):
337+ with self .subTest (size = prealloc ):
338+ writer = self .create_writer (prealloc )
339+ writer .update (items1 + common )
340+ writer .update (common + items2 )
341+ self .frozenset_equal (writer .finish (), expected )
305342
306343 def test_finish (self ):
307344 # Test PyFrozenSetWriter_Finish(): track the frozenset in the GC if at
0 commit comments