标签:style class blog code http tar
本文为senlie原创,转载请保留此地址:http://blog.csdn.net/zhengsenlie
1.python的执行过程
1)对python源代码进行编译,产生字节码
2)将编译结果交给python虚拟机,由虚拟机按照顺序一条一条地执行字节码,产生执行结果
图7-1
2.Python编译器的编译结果——PyCodeObject对象
Python编译器的编译结果中包含了字符串、常量值、字节码等在源代码中出现的一切有用的静态信息。
在Python运行期间,这些静态信息被PyCodeObject对象中
在Python运行结束后,这些信息会被存储在pyc文件中
PyCodeObject对象和pyc文件是Python对源文件编译结果的两种不同存在形式
3.Python源码中的PyCodeObject
/* Bytecode object */ typedef struct { PyObject_HEAD int co_argcount; /* 位置参数个数*/ int co_nlocals; /* 局部变量个数,包括位置参数个数*/ int co_stacksize; /* 需要的栈空间 */ int co_flags; /* CO_..., see below */ PyObject *co_code; /* 字节码指令序列,以PyStringObject形式存在 */ PyObject *co_consts; /* PyTupleObject对象,保存所有的常量 */ PyObject *co_names; /* PyTupleObject对象,保存所有符号 */ PyObject *co_varnames; /* 局部变量名集合 */ PyObject *co_freevars; /* 实现闭包需要用到的东西 */ PyObject *co_cellvars; /* 内部嵌套函数所引用的局部变量名集合 */ /* The rest doesn't count for hash/cmp */ PyObject *co_filename; /* Code Block所对应的.py文件的完整路径 */ PyObject *co_name; /* Code Block的名字,通常是函数名或类名 */ int co_firstlineno; /* Code Block所对应的.py文件的起始行 */ PyObject *co_lnotab; /* 字节码指令与.py文件中source code行号的对应关系,以PyStringObject的等式存在 */ void *co_zombieframe; /* for optimization only (see frameobject.c) */ PyObject *co_weakreflist; /* to support weakrefs to code objects */ } PyCodeObject;
#会产生三个 PyCodeObject,分别对应整个文件,class A和 def Fun class A: pass def Fun(): pass a = A() Fun()
static void w_object(PyObject *v, WFILE *p) { //…… else if (PyCode_Check(v)) { PyCodeObject *co = (PyCodeObject *)v; w_byte(TYPE_CODE, p); w_long(co->co_argcount, p); w_long(co->co_nlocals, p); w_long(co->co_stacksize, p); w_long(co->co_flags, p); w_object(co->co_code, p); w_object(co->co_consts, p); w_object(co->co_names, p); w_object(co->co_varnames, p); w_object(co->co_freevars, p); w_object(co->co_cellvars, p); w_object(co->co_filename, p); w_object(co->co_name, p); w_long(co->co_firstlineno, p); w_object(co->co_lnotab, p); } //…… }
typedef struct { FILE *fp; PyObject *strings; //在写入时指向dict,在读出时指向list } WFILE;
//w_object对于字符串的处理 else if (PyString_CheckExact(v)) { if (p->strings && PyString_CHECK_INTERNED(v)) { //[1]:获得 PyStringObject对象在strings中的序号 PyObject *o = PyDict_GetItem(p->strings, v); //[2]:intern字符串的非首次写入 if (o) { long w = PyInt_AsLong(o); w_byte(TYPE_STRINGREF, p); w_long(w, p); goto exit; } //[3]:intern字符串的首次写入 else { int ok; o = PyInt_FromSsize_t(PyDict_Size(p->strings)); ok = o && PyDict_SetItem(p->strings, v, o) >= 0; Py_XDECREF(o); if (!ok) { p->depth--; p->error = WFERR_UNMARSHALLABLE; return; } w_byte(TYPE_INTERNED, p); } } //[4]:写入普通字符串 else { w_byte(TYPE_STRING, p); } //写入字符串 w_pstring(PyBytes_AS_STRING(v), PyString_GET_SIZE(v), p); } //...
STOP_CODE() Indicates end-of-code to the compiler, not used by the interpreter. NOP() Do nothing code. Used as a placeholder by the bytecode optimizer. POP_TOP() Removes the top-of-stack (TOS) item. ROT_TWO() Swaps the two top-most stack items. ROT_THREE() Lifts second and third stack item one position up, moves top down to position three. ROT_FOUR() Lifts second, third and forth stack item one position up, moves top down to position four. //...
《python源码剖析》笔记 Python的编译结果,布布扣,bubuko.com
标签:style class blog code http tar
原文地址:http://blog.csdn.net/zhengsenlie/article/details/31015635