1 PyObject, PyTypeObject - Python 中的 '对象' 们
2
3 '一切皆对象' - 这是 Python 的学习和使用者们最最常听到一句, 可谓 博大精深 - '勃大精深'.
4 '对象(Object)' 是 Python 最核心的一个概念, 在 Python 中 '一切皆是对象'.
5 整数,字符串,类型type(整数类型, 字符串类型)统统都是'对象'.
6
7 Python 已经预先定义了一些'类型对象', 如 int 类型, dict 类型, string 类型等等,
8 这些预先定义的类型对象被称为'内建类型对象'. '类型对象' 实现了面向对象理论中'类'的概念,
9 通过对类型对象的 '实例化' 创建'实例对象', 如 int 对象, dict 对象, string 对象等.
10 '实例对象'可以被视为面向对象理论中'对象'这个概念在 python 中的体现.
11 另外, python 实现了通过 class A(object) 关键字实现自定义类型对象, 通过调用自定义的类型对象实例化类型对象 A().
12 注: python '类型'(type) -> '类'(class) ; python '实例'(instance) -> '对象'(object)
13
14 怎样理解 '对象'(object) 的概念
15 ‘对象’ 这一概念对人的思维是一个比较形象的概念, 然后计算机不能像人的思维一样去'理解'对象这一概念.
16 计算机并不能理解 3 是一个整数, 而 '3' 是一个字符串, 对于它来说这些都是'字节'(byte).
17 通常, '对象' 是数据以及基于这些数据的操作的集合. 对于计算机来说, 一个 '对象' 实际上就是一片被分配的内存空间,
18 这些内存可以是连续的, 也可以是离散的. 这片内存在更高的层面上被作为一个'整体'来考虑和处理, 这个整体就是一个'对象'(对计算机来说)
19 而在这片内存中存储着一系列的数据以及可以对这些数据进行操作(修改,读取,运行等)的代码(字节码).
20
21 如大家所知道的那样, Python 是有 C 实现的, 那么'对象' 在 C 层面是什么样子呢?
22 PyObject 对象
23 Python 中, '对象' 就是为 C 中的结构体(structure)在栈堆上申请的一块儿内存区域.
24 object.h (Python 3.6)
25 typedef struct _object {
26 _PyObject_HEAD_EXTRA
27 Py_ssize_t ob_refcnt; # ob_refcnt 引用计数(垃圾回收机制)
28 struct _typeobject *ob_type; # ob_type 是一个指向 _typeobject 结构体的指针
29 } PyObject;
30 在 C 中定义 PyObject 结构体中 ob_refcnt 与 Python 内存管理机制有关, 它实现了基于 '引用计数' 的 '垃圾回收机制‘.
31 对于某一特定对象 A, 当有另一个 PyObject '引用' 了该对象的时候, A 的'引用计数'( ob_refcnt ) 增加;
32 相反地, 如果 当这个 PyObject 被销毁的时候, 对象 A 的'引用计数'( ob_refcnt ) 减少.
33 当对象 A 的'引用计数'( ob_refcnt ) 减少到 0 的时候, Python 的垃圾回收机制将把对象 A 从栈堆中删除, 以便释放内存供其他对象使用.
34 除 '引用计数'( ob_refcnt ) 之外, ob_type 是一个指向 _typeobject 结构体的指针.
35 这个结构体对应着 Python 内部的一种特殊对象, 用来指定一个'对象' 类型的 '类型对象', 如 对象 5 的类型对象 是 int 类型对象.
36 结论, 在 Python 中, 对象机制的核心, 一是 '引用计数'( ob_refcnt ), 另一个是 '类型信息'(ob_type).
37 通过'类型信息'(ob_type) 进一步对应到 一个对象的'内容','大小' 等信息.
38
39 PyTypeObject 类型信息
40 PyObject 中包括了所有'对象' 共有的信息的定义(ob_refcnt, ob_type).
41 在结构体 _typeobject 中, 主要定义了 4 类信息,
42 1, 类型名(tp_name), 主要供 Python 内部, 以及调试使用.
43 2, 创建该类型'对象' 时分配的内存空间相关信息, 即 tp_basicsize, tp_itemsize
44 3, 与该类型'对象'相关联的操作信息, 如 tp_print; tp_getattr; tp_setattr 这些函数指针
45 4, 该类型对象的'类型信息' (通过 PyType_Type 来确定一个对象的 '类型对象')
46
47 object.h (Python 3.6)
48 typedef struct _typeobject {
49 PyObject_VAR_HEAD
50 const char *tp_name; /* For printing, in format "<module>.<name>" */
51 Py_ssize_t tp_basicsize, tp_itemsize; /* For allocation */
52
53 /* Methods to implement standard operations */
54 destructor tp_dealloc;
55 printfunc tp_print;
56 getattrfunc tp_getattr;
57 setattrfunc tp_setattr;
58 PyAsyncMethods *tp_as_async; /* formerly known as tp_compare (Python 2)
59 or tp_reserved (Python 3) */
60 reprfunc tp_repr;
61
62 /* Method suites for standard classes */
63 PyNumberMethods *tp_as_number;
64 PySequenceMethods *tp_as_sequence;
65 PyMappingMethods *tp_as_mapping;
66
67 /* More standard operations (here for binary compatibility) */
68 hashfunc tp_hash;
69 ternaryfunc tp_call;
70 reprfunc tp_str;
71 getattrofunc tp_getattro;
72 setattrofunc tp_setattro;
73
74 /* Functions to access object as input/output buffer */
75 PyBufferProcs *tp_as_buffer;
76
77 /* Flags to define presence of optional/expanded features */
78 unsigned long tp_flags;
79
80 const char *tp_doc; /* Documentation string */
81
82 /* Assigned meaning in release 2.0 */
83 /* call function for all accessible objects */
84 traverseproc tp_traverse;
85
86 /* delete references to contained objects */
87 inquiry tp_clear;
88
89 /* Assigned meaning in release 2.1 */
90 /* rich comparisons */
91 richcmpfunc tp_richcompare;
92
93 /* weak reference enabler */
94 Py_ssize_t tp_weaklistoffset;
95
96 /* Iterators */
97 getiterfunc tp_iter;
98 iternextfunc tp_iternext;
99
100 /* Attribute descriptor and subclassing stuff */
101 struct PyMethodDef *tp_methods;
102 struct PyMemberDef *tp_members;
103 struct PyGetSetDef *tp_getset;
104 struct _typeobject *tp_base;
105 PyObject *tp_dict;
106 descrgetfunc tp_descr_get;
107 descrsetfunc tp_descr_set;
108 Py_ssize_t tp_dictoffset;
109 initproc tp_init;
110 allocfunc tp_alloc;
111 newfunc tp_new;
112 freefunc tp_free; /* Low-level free-memory routine */
113 inquiry tp_is_gc; /* For PyObject_IS_GC */
114 PyObject *tp_bases;
115 PyObject *tp_mro; /* method resolution order */
116 PyObject *tp_cache;
117 PyObject *tp_subclasses;
118 PyObject *tp_weaklist;
119 destructor tp_del;
120
121 /* Type attribute cache version tag. Added in version 2.6 */
122 unsigned int tp_version_tag;
123
124 destructor tp_finalize;
125
126 #ifdef COUNT_ALLOCS
127 /* these must be last and never explicitly initialized */
128 Py_ssize_t tp_allocs;
129 Py_ssize_t tp_frees;
130 Py_ssize_t tp_maxalloc;
131 struct _typeobject *tp_prev;
132 struct _typeobject *tp_next;
133 #endif
134 } PyTypeObject;