at the discretion of the garbage collector, and might never occur. This contrasts with destructors, which are called deterministically as soon as an object is no longer in use, and are always called, except in case of uncontrolled program termination. Finalizers are most frequently instance methods, due to needing to do object-specific operations. The garbage collector must also account for the possibility of object resurrection. Most commonly this is done by first executing finalizers, then checking whether any objects have been resurrected, and if so, aborting their destruction. This additional check is potentially expensive – a simple implementation re-checks all garbage if even a single object has a finalizer – and thus both slows down and complicates garbage collection. For this reason, objects with finalizers may be collected less frequently than objects without finalizers (only on certain cycles), exacerbating problems caused by relying on prompt finalization, such as resource leaks. If an object is resurrected, there is the further question of whether its finalizer is called again, when it is next destroyed – unlike destructors, finalizers are potentially called multiple times. If finalizers are called for resurrected objects, objects may repeatedly resurrect themselves and be indestructible; this occurs in the CPython implementation of Python prior to Python 3.4, and in CLR languages such as C#. To avoid this, in many languages, including Java, Objective-C (at least in recent Apple implementations), and Python from Python 3.4, objects are finalized at most once, which requires tracking if the object has been finalized yet. In other cases, notably CLR languages like C#, finalization is tracked separately from the objects themselves, and objects can be repeatedly registered or deregistered for finalization. Problems Depending on the implementation, finalizers can cause a significant number of problems, and are thus strongly discouraged by a number of authorities. These problems include: Finalizers may not be called in a timely manner, or at all, so they cannot be relied upon to persist state, release scarce resources, or do anything else of importance. Finalizers may result in object resurrection, which is often a programming error and whose very possibility significantly slows down and complicates garbage collection. Finalizers are run based on garbage collection, which is generally based on managed memory pressure – they are not run in case of other resource scarcity, and thus are not suited for managing other scarce resources. Finalizers do not run in a specified order,