this is a question about python generational garbage collection
With below code I expect 10k objects (times three) from last get_count call:
import gc
print(gc.get_threshold())
print(gc.get_count())
print(gc.collect())
print(gc.get_count())
class Dummy:
def __init__(self) -> None:
pass
list = []
for i in range(10000):
list.append(Dummy())
print(gc.get_count())
print(gc.collect())
for i in range(10000):
list.append(Dummy())
print(gc.get_count())
print(gc.collect())
for i in range(10000):
list.append(Dummy())
print(gc.get_count())
print(gc.collect())
But it didn't.
(700, 10, 10)
(415, 0, 9)
391
(259, 0, 0)
(54, 3, 1)
287
(522, 2, 1)
35
(526, 2, 1)
The GC classifies objects into three generations depending on how many collection sweeps they have survived. New objects are placed in the youngest generation (generation 0). If an object survives a collection it is moved into the next older generation. Since generation 2 is the oldest generation, objects in that generation remain there after a collection. In order to decide when to run, the collector keeps track of the number object allocations and deallocations since the last collection. When the number of allocations minus the number of deallocations exceeds threshold0, collection starts. Initially only generation 0 is examined. If generation 0 has been examined more than threshold1 times since generation 1 has been examined, then generation 1 is examined as well. With the third generation, things are a bit more complicated, see Collecting the oldest generation for more information.
You've misunderstood what gc.get_count()
does. It returns the values of the counters used to determine when a GC pass happens. The 3 counters track progress toward a generation 0 collection, a generation 1 collection, and a generation 2 collection respectively.
Progress toward a generation 0 collection is incremented when an object becomes GC-tracked, and decremented when a GC-tracked object is deallocated (unless decrementing the counter would bring it below 0). Progress toward a generation 1 collection is incremented after a generation 0 collection. Progress toward a generation 2 collection is incremented after a generation 1 collection. When a generation is collected, its counter is reset.
The counters are not counts of numbers of objects created. The first counter is closest to being that, but even that counter isn't a count of objects created. Plus, GC passes happen automatically, not just when you explicitly trigger one, so the counts wouldn't have the values you expected even if they had the meanings you expected.