2006年04月13日 星期四 18:57
ext手册上2.1.1节有个例子: static int Noddy_init(Noddy *self, PyObject *args, PyObject *kwds) { PyObject *first=NULL, *last=NULL, *tmp; static char *kwlist[] = {"first", "last", "number", NULL}; if (! PyArg_ParseTupleAndKeywords(args, kwds, "|OOi", kwlist, &first;, &last;, &self-;>number)) return -1; if (first) { tmp = self->first; Py_INCREF(first); self->first = first; Py_XDECREF(tmp); } if (last) { tmp = self->last; Py_INCREF(last); self->last = last; Py_XDECREF(tmp); } return 0; } 它说这里对first和last成员的赋值很讲究,一定要先赋值,再减引用计数,理由是: But this would be risky. Our type doesn't restrict the type of the first member, so it could be any kind of object. It could have a destructor that causes code to be executed that tries to access the first member. To be paranoid and protect ourselves against this possibility, we almost always reassign members before decrementing their reference counts. When don't we have to do this? 不知我理解错了意思没有,我觉得它是说如果先减引用计数,就有可能导致self->first的计数为0从而被析构,而析构函数中可能会有代码又对first成员进行操作。这就有两不懂了, 一、就算它析构函数里又对它自己做某些操作有什么关系呢? 二、先减引用计数和后减有什么区别呢?如果它计数现在是1,那么后减也会导致被析构,没有什么区别啊? 请各位指教了,多谢多谢! -------------- next part -------------- An HTML attachment was scrubbed... URL: http://lists.exoweb.net/pipermail/python-chinese/attachments/20060413/79f2f8d3/attachment.html
2006年04月18日 星期二 14:05
考虑这个情况:self->first的引用计数已经是1,而且它在析构函数里访问first, 不巧这个访问导致first被重新allocate,所以first会主动去把所有引用first的 指针修改成新的地址; 这种情况下,如果先减self->first的引用计数,再把first的值赋给self->first, 那么self->first里面最后保留的是一个无效的值。 这个例子构造的有些偏了,也许有更好的解释。 -- regards, yzhh
Zeuux © 2025
京ICP备05028076号