← index #1878PR #18005
Duplicate · high · value 0.257
QUERY · ISSUE

py: __del__ special method not implemented for user-defined classes

openby israelg99opened 2016-03-07updated 2024-12-05
py-core

Example:

import gc

class Foo():
    def __del__(self):
        print('__del__')

f = Foo()
del f

gc.collect()

According to this post #1802, gc.collect() should collect the object after the del and call the finaliser, but the finaliser is never called, any ideas?

I know that a good programming practice is to assume that __del__ may never be called, but hey, this still should work :)

CANDIDATE · PULL REQUEST

py/objtype: Implement __del__ data model method for user classes.

openby AJMansfieldopened 2025-08-29updated 2026-03-03
py-core

Summary

This PR implements the required functionality to allow the garbage collector to run user-defined __del__ methods as finalisers.

Testing

I've added full-coverage tests of this feature that I've tested for sensitivity across both the Unix port and my RP2040 and RP2350 boards. All tests pass in all the environments I've tested it in.

Note that the test is specifically designed to tolerate an expected number of failures, due to the fact that the GC is conservative and doesn't make much in the way of guarantees. Out of the 100 create/delete cycles in its checking phase, it allows up to 2 of their finalisers to be missed run. I've only observed cases where a single object's finaliser was missed, so I've set this threshold as 1 higher than that to ensure the test doesn't become another low-selectivity thorn in the CI.

Trade-offs and Alternatives

This PR claims two additional bits from the mp_obj_type_t.flags field, for MP_TYPE_FLAG_IS_INSTANCED and MP_TYPE_FLAG_HAS_FINALISER. The latter bit is required in order to track whether instances should be allocated using the _with_finaliser allocators, while the former is required to track whether it's still safe to allow the __del__ method to be inserted into a class after-the-fact. It's possible that MP_TYPE_FLAG_IS_INSTANCED could be eliminated by forbidding this type of insertion entirely.

With the addition of the MP_TYPE_FLAG_HAS_FINALISER bit, it might be possible to make use of this flag in the finaliser lookup code, as a cheaper way to fail out than a lookup miss; but this would be redundant with the FTB table check.

As another alternative, this could be re-implemented to make the finaliser into an object slot, though this would make all type objects larger.

References

Fixes: #1878

PEP 442 – Safe object finalization

See also:

  • #1878
  • #646
  • #2621
  • #17142

Keyboard

j / / n
next pair
k / / p
previous pair
1 / / h
show query pane
2 / / l
show candidate pane
c
copy suggested comment
r
toggle reasoning
g i
go to index
?
show this help
esc
close overlays

press ? or esc to close

copied