类型对象
类型对象
Python 对象系统中最重要的一个结构体也许是定义新类型的结构体: PyTypeObject 结构体。 类型对象可以使用任何 PyObject_* 或 PyType_* 函数来处理,但并未提供大多数 Python 应用程序会感兴趣的东西。 这些对象是对象行为的基础,所以它们对解释器本身及任何实现新类型的扩展模块都非常重要。
与大多数标准类型相比,类型对象相当大。这么大的原因是每个类型对象存储了大量的值,大部分是C函数指针,每个指针实现了类型功能的一小部分。本节将详细描述类型对象的字段。这些字段将按照它们在结构中出现的顺序进行描述。
除了下面的快速参考, 例子 小节提供了快速了解 PyTypeObject 的含义和用法的例子。
快速参考
“tp 槽位”
| PyTypeObject 槽位 [1] | 类型 | 特殊方法/属性 | 信息 [2] |
|---|---|---|---|
| O | T | D | I |
| <R> tp name | const char __ | name | X |
| tp basicsize | Py _ssize _t__ | X | |
| tp itemsize | Py _ssize _t__ | ||
| tp dealloc | destructor | X | |
| tp vectorcall_offset | Py_ssize_t | ||
| (tp_getattr) | getattrfunc | __getattribute, __getattr | |
| (tp_setattr) | setattrfunc | __setattr, __delattr | |
| tp_as_async | PyAsyncMethods | 子槽位 | |
| tp repr | reprfunc | repr | X |
| tp _as _number__ | PyNumberMethods __ | 子槽位 | |
| tp_as_sequence | PySequenceMethods | 子槽位 | |
| tp _as _mapping__ | PyMappingMethods __ | 子槽位 | |
| tp hash | hashfunc | hash | X |
| tp call | ternaryfunc | call | |
| tp str | reprfunc | str | X |
| tp getattro | getattrofunc | getattribute , getattr | X |
| tp_setattro | setattrofunc | __setattr, __delattr | X |
| tp_as_buffer | PyBufferProcs | ||
| tp flags | unsigned long | X | |
| tp doc | const char __ | doc | X |
| tp traverse | traverseproc | ||
| tp clear | inquiry | ||
| tp richcompare | richcmpfunc | lt , le , eq , ne , gt , ge | X |
| (tp weaklistoffset ) | Py_ssize_t | ||
| tp_iter | getiterfunc | __iter | |
| tp_iternext | iternextfunc | __next | |
| tp_methods | PyMethodDef [] | X | |
| tp_members | PyMemberDef [] | ||
| tp_getset | PyGetSetDef [] | X | |
| tp_base | PyTypeObject | base | |
| tp dict | PyObject * | dict | |
| tp _descr _get__ | descrgetfunc | get | |
| tp _descr _set__ | descrsetfunc | set , __delete_ | |
| (tp_dictoffset) | Py_ssize_t | ||
| tp_init | initproc | __init | X |
| tp_alloc | allocfunc | X | |
| tp_new | newfunc | __new | X |
| tp_free | freefunc | X | |
| tp_is_gc | inquiry | ||
| <tp_bases> | PyObject * | __bases | |
| <tp_mro> | PyObject * | __mro | |
| [tp_cache] | PyObject __ | ||
| [tp_subclasses] | void | __subclasses | |
| [tp_weaklist] | PyObject * | ||
| (tp_del) | destructor | ||
| [tp_version_tag] | unsigned int | ||
| tp_finalize | destructor | __del | |
| tp_vectorcall | vectorcallfunc | ||
| [tp_watched] | unsigned char |
[1]
() :括号中的插槽名称表示(实际上)已弃用。
< >: 尖括号内的名称在初始时应设为 NULL 并被视为是只读的。
[] : 方括号内的名称仅供内部使用。
< R> (作为前缀) 表示字段是必需的 (不能是 NULL)。
[2]
列:
“O” : 在 PyBaseObject_Type 上设置
“T” : 在 PyType_Type 上设置
“D” : 默认设置(如果方法槽被设置为NULL)
X - PyType_Ready 如其为 NULL 则设置该值
~ - PyType_Ready 始终设置该值 (它应当为 NULL)
? - PyType_Ready 根据其他槽位可能设置该值
另请参阅继承列 ("I")。
“I” : 继承
X - 如果使用 *NULL* 值定义则类型槽位将通过 *PyType_Ready* 继承
% - 子结构体的槽位是单独继承的
G - 已继承,但仅会与其他槽位相结合;参见槽位的说明
? - 较复杂;参见槽位的说明
注意,有些方法槽是通过普通属性查找链有效继承的。
子槽位
| 槽位 | 类型 | 特殊方法 |
|---|---|---|
| am await | unaryfunc | await |
| am aiter | unaryfunc | aiter |
| am anext | unaryfunc | anext |
| am send | sendfunc | |
| nb add | binaryfunc | add radd |
| nb _inplace _add__ | binaryfunc | iadd |
| nb subtract | binaryfunc | sub rsub |
| nb _inplace _subtract__ | binaryfunc | isub |
| nb multiply | binaryfunc | mul rmul |
| nb _inplace _multiply__ | binaryfunc | imul |
| nb remainder | binaryfunc | mod rmod |
| nb _inplace _remainder__ | binaryfunc | imod |
| nb divmod | binaryfunc | divmod rdivmod |
| nb power | ternaryfunc | pow rpow |
| nb _inplace _power__ | ternaryfunc | ipow |
| nb negative | unaryfunc | neg |
| nb positive | unaryfunc | pos |
| nb absolute | unaryfunc | abs |
| nb bool | inquiry | bool |
| nb invert | unaryfunc | invert |
| nb lshift | binaryfunc | lshift rlshift |
| nb _inplace _lshift__ | binaryfunc | ilshift |
| nb rshift | binaryfunc | rshift rrshift |
| nb _inplace _rshift__ | binaryfunc | irshift |
| nb and | binaryfunc | and rand |
| nb _inplace _and__ | binaryfunc | iand |
| nb xor | binaryfunc | xor rxor |
| nb _inplace _xor__ | binaryfunc | ixor |
| nb or | binaryfunc | or ror |
| nb _inplace _or__ | binaryfunc | ior |
| nb int | unaryfunc | int |
| nb reserved | void * | |
| nb float | unaryfunc | __float_ |
| nb_floor_divide | binaryfunc | __floordiv |
| nb_inplace_floor_divide | binaryfunc | __ifloordiv |
| nb_true_divide | binaryfunc | __truediv |
| nb_inplace_true_divide | binaryfunc | __itruediv |
| nb_index | unaryfunc | __index |
| nb_matrix_multiply | binaryfunc | __matmul __rmatmul |
| nb_inplace_matrix_multiply | binaryfunc | __imatmul |
| mp_length | lenfunc | __len |
| mp_subscript | binaryfunc | __getitem |
| mp_ass_subscript | objobjargproc | __setitem, __delitem |
| sq_length | lenfunc | __len |
| sq_concat | binaryfunc | __add |
| sq_repeat | ssizeargfunc | __mul |
| sq_item | ssizeargfunc | __getitem |
| sq_ass_item | ssizeobjargproc | __setitem __delitem |
| sq_contains | objobjproc | __contains |
| sq_inplace_concat | binaryfunc | __iadd |
| sq_inplace_repeat | ssizeargfunc | __imul |
| bf_getbuffer | getbufferproc() | |
| bf_releasebuffer | releasebufferproc() |
槽位 typedef
| typedef | 参数类型 | 返回类型 |
|---|---|---|
| allocfunc | PyTypeObject ___Py_ssize_t_ | PyObject |
| destructor | PyObject __ | void |
| freefunc | void | void |
| traverseproc | PyObject ___visitproc _void | int |
| newfunc | PyObject ___PyObject _PyObject __ | PyObject |
| initproc | PyObject ___PyObject _PyObject __ | int |
| reprfunc | PyObject | PyObject __ |
| getattrfunc | PyObject const char __ | PyObject |
| setattrfunc | PyObject ___const char_PyObject __ | int |
| getattrofunc | PyObject PyObject __ | PyObject |
| setattrofunc | PyObject ___PyObject _PyObject __ | int |
| descrgetfunc | PyObject PyObject ___PyObject _ | PyObject __ |
| descrsetfunc | PyObject PyObject ___PyObject _ | int |
| hashfunc | PyObject __ | Py_hash_t |
| richcmpfunc | PyObject PyObject ___int_ | PyObject |
| getiterfunc | PyObject __ | PyObject |
| iternextfunc | PyObject __ | PyObject |
| lenfunc | PyObject __ | Py_ssize_t |
| getbufferproc | PyObject Py_buffer ___int_ | int |
| releasebufferproc | PyObject Py_buffer __ | void |
| inquiry | PyObject | int |
| unaryfunc | PyObject __ | PyObject |
| binaryfunc | PyObject ___PyObject _ | PyObject __ |
| ternaryfunc | PyObject PyObject ___PyObject _ | PyObject __ |
| ssizeargfunc | PyObject Py_ssize_t | PyObject __ |
| ssizeobjargproc | PyObject Py_ssize_tPyObject __ | int |
| objobjproc | PyObject PyObject __ | int |
| objobjargproc | PyObject PyObject ___PyObject _ | int |
请参阅 槽位类型 typedef 里有更多详细信息。
PyTypeObject 定义
PyTypeObject 的结构定义可以在 Include/object.h 中找到。 为了方便参考,此处复述了其中的定义:
typedef struct _typeobject {
PyObject_VAR_HEAD
const char *tp_name; /* 用于打印,格式为 "<module>.<name>" */
Py_ssize_t tp_basicsize, tp_itemsize; /* 用于分配 */
/* 用于实现标准操作的方法 */
destructor tp_dealloc;
Py_ssize_t tp_vectorcall_offset;
getattrfunc tp_getattr;
setattrfunc tp_setattr;
PyAsyncMethods *tp_as_async; /* 原名为 tp_compare (Python 2)
或 tp_reserved (Python 3) */
reprfunc tp_repr;
/* 用于标准类的方法集 */
PyNumberMethods *tp_as_number;
PySequenceMethods *tp_as_sequence;
PyMappingMethods *tp_as_mapping;
/* 更多标准操作(这些用于二进制兼容) */
hashfunc tp_hash;
ternaryfunc tp_call;
reprfunc tp_str;
getattrofunc tp_getattro;
setattrofunc tp_setattro;
/* 用于以输入/输出缓冲区方式访问对象的函数 */
PyBufferProcs *tp_as_buffer;
/* 用于定义可选/扩展特性是否存在的旗标 */
unsigned long tp_flags;
const char *tp_doc; /* 文档字符串 */
/* 在 2.0 发布版中分配的含义 */
/* 为所有可访问的对象调用函数 */
traverseproc tp_traverse;
/* 删除对所包含对象的引用 */
inquiry tp_clear;
/* 在 2.1 发布版中分配的含义 */
/* 富比较操作 */
richcmpfunc tp_richcompare;
/* 弱引用的启用 */
Py_ssize_t tp_weaklistoffset;
/* 迭代器 */
getiterfunc tp_iter;
iternextfunc tp_iternext;
/* 属性描述器和子类化内容 */
struct PyMethodDef *tp_methods;
struct PyMemberDef *tp_members;
struct PyGetSetDef *tp_getset;
// 堆类型的强引用,静态类型的借入引用
struct _typeobject *tp_base;
PyObject *tp_dict;
descrgetfunc tp_descr_get;
descrsetfunc tp_descr_set;
Py_ssize_t tp_dictoffset;
initproc tp_init;
allocfunc tp_alloc;
newfunc tp_new;
freefunc tp_free; /* 低层级的释放内存例程 */
inquiry tp_is_gc; /* For PyObject_IS_GC */
PyObject *tp_bases;
PyObject *tp_mro; /* 方法解析顺序 */
PyObject *tp_cache;
PyObject *tp_subclasses;
PyObject *tp_weaklist;
destructor tp_del;
/* 类型属性缓存版本标签。 在 2.6 版中添加 */
unsigned int tp_version_tag;
destructor tp_finalize;
vectorcallfunc tp_vectorcall;
/* 类型监视器针对此类型的位设置 */
unsigned char tp_watched;
} PyTypeObject;
PyObject 槽位
类型对象结构体扩展了 PyVarObject 结构体。 ob_size 字段用于动态类型(由 type_new() 创建,通常由 class 语句调用)。 请注意 PyType_Type (元类型)会初始化 tp_itemsize,这意味着它的实例(即类型对象) 必须 具有 ob_size 字段。
Py_ssize_t PyObject.ob_refcnt
属于稳定 ABI.
这是类型对象的引用计数,由 PyObject_HEAD_INIT 宏初始化为 1。 请注意对于 静态分配的类型对象,类型的实例(其 ob_type 指向该类型的对象) 不会被 计入引用。 但对于 动态分配的类型对象,实例 会被 计入引用。
继承:
子类型不继承此字段。
PyTypeObject *PyObject.ob_type
属于稳定 ABI.
这是类型的类型,换句话说就是元类型,它由宏 PyObject_HEAD_INIT 的参数来做初始化,它的值一般情况下是 &PyType_Type 。可是为了使动态可载入扩展模块至少在Windows上可用,编译器会报错这是一个不可用的初始化。因此按照惯例传递 NULL 给宏 PyObject_HEAD_INIT 并且在模块的初始化函数开始时候其他任何操作之前初始化这个字段。典型做法是这样的:
Foo_Type.ob_type = &PyType_Type;
这应当在创建类型的任何实例之前完成。 PyType_Ready() 会检查 ob_type 是否为 NULL,如果是,则将其初始化为基类的 ob_type 字段。 如果该字段为非零值则 PyType_Ready() 将不会更改它。
继承:
此字段会被子类型继承。
PyVarObject 槽位
Py_ssize_t PyVarObject.ob_size
属于稳定 ABI.
对于 静态分配的内存对象,它应该初始化为 0。对于 动态分配的类型对象,该字段具有特殊的内部含义。
继承:
子类型不继承此字段。
(本文超出站点单文档体积上限,已按小节截断)
