Skip to content

Commit

Permalink
Add an example sketch from Petr Viktorin
Browse files Browse the repository at this point in the history
  • Loading branch information
colesbury authored Jan 20, 2025
1 parent 37a08dc commit f5507d8
Showing 1 changed file with 39 additions and 3 deletions.
42 changes: 39 additions & 3 deletions Doc/c-api/object.rst
Original file line number Diff line number Diff line change
Expand Up @@ -632,9 +632,45 @@ Object Protocol
}
return 0;
This is intended as a building block for safely dealing with
:term:`borrowed references <borrowed reference>` without the overhead of
creating a :c:type:`!PyWeakReference`.
This is intended as a building block for managing weak references
without the overhead of a Python :c:type:`!PyWeakReference`.
Typically, correct use of this function requires support from *obj*'s
deallocator (:c:member:`~PyTypeObject.tp_dealloc`).
For example, the following sketch could be adapted to implement a
"weakmap" that works like a :py:class:`~weakref.WeakValueDictionary`
for a specific type:
.. code-block:: c
PyObject *
get_value(weakmap_key_type *key)
{
weakmap_type weakmap = ...;
weakmap_lock_mutex(weakmap);
PyObject *result = weakmap_find(weakmap, key);
if (PyUnstable_TryIncRef(result)) {
// `result` is safe to use
weakmap_unlock_mutex(weakmap);
return result;
}
// if we get here, `result` is starting to be garbage-collected,
// but has not been removed from the weakmap yet
weakmap_unlock_mutex(weakmap->mutex);
return NULL;
}
// tp_dealloc function for weakmap values
void
value_dealloc(PyObject *value)
{
weakmap_type weakmap = ...;
weakmap_lock_mutex(weakmap);
weakmap_remove_value(weakmap, value);
...
weakmap_unlock_mutex(weakmap);
}
.. versionadded:: 3.14
Expand Down

0 comments on commit f5507d8

Please sign in to comment.