在 Python (2.7) 中,为什么 os.remove 与 os.unlink 不同? [英] In Python (2.7), why is os.remove not identical to os.unlink?

查看:38
本文介绍了在 Python (2.7) 中,为什么 os.remove 与 os.unlink 不同?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

<预><代码>>>>导入系统>>>系统版本'2.7.3(默认,2014 年 3 月 13 日,11:03:55)\n[GCC 4.7.2]'>>>导入操作系统>>>os.remove 是 os.unlink错误的>>>os.remove == os.unlink真的

这是为什么?os.unlink 不应该是 os.remove 的别名吗?

解决方案

要回答这个问题,我们必须深入了解 Python 解释器的工作原理.在其他 Python 实现中可能会有所不同.

首先让我们从定义 os.removeos.unlink 函数的位置开始.在 Modules/posixmodule.c 中,它们注册为:

{"unlink", posix_unlink, METH_VARARGS, posix_unlink__doc__},{删除",posix_unlink,METH_VARARGS,posix_remove__doc__},

请注意,函数指针都指向 ml_meth 成员中的 posix_unlink.

对于方法对象,== 相等运算符由 meth_richcompare(...)对象/methodobject.c.

它包含这个逻辑,这解释了为什么 == 运算符返回 True.

a = (PyCFunctionObject *)self;b = (PyCFunctionObject *)other;eq = a->m_self == b->m_self;如果(等式)eq = a->m_ml->ml_meth == b->m_ml->ml_meth;

对于内置函数,m_selfNULL,所以 eqtrue 开始.然后我们比较 ml_meth 中的函数指针(从上面的结构引用相同的 posix_unlink),因为它们匹配 eq 保持 true.最终结果是python返回True.

is 运算符更简单也更严格.is 运算符仅比较 PyCFunctionObj* 指针.它们会有所不同——它们来自不同的结构并且是不同的对象,因此 is 运算符将返回 False.

基本原理可能是它们是单独的函数对象(回想一下它们的文档字符串是不同的)但它们指向相同的实现,因此 is==是合理的.

is 带来了更强的保证,并且意味着快速和廉价(本质上是指针比较).== 运算符检查对象并在其内容匹配时返回 True.在这种情况下,函数指针就是内容.

>>> import sys
>>> sys.version
'2.7.3 (default, Mar 13 2014, 11:03:55) \n[GCC 4.7.2]'
>>> import os
>>> os.remove is os.unlink
False
>>> os.remove == os.unlink
True

Why is that? Isn't os.unlink supposed to be an alias of os.remove?

解决方案

To answer this question we have to dive a bit into the details of how the python interpreter works. It might be different in other python implementations.

First let's start where the os.remove and os.unlink functions are defined. In Modules/posixmodule.c they are registered as:

{"unlink",          posix_unlink, METH_VARARGS, posix_unlink__doc__},
{"remove",          posix_unlink, METH_VARARGS, posix_remove__doc__},

Note that the function pointers both point to posix_unlink in their ml_meth member.

For method objects, the == equality operator is implemented by meth_richcompare(...) in Objects/methodobject.c.

It contains this logic, which explains why the == operator returns True.

a = (PyCFunctionObject *)self;
b = (PyCFunctionObject *)other;
eq = a->m_self == b->m_self;
if (eq)
    eq = a->m_ml->ml_meth == b->m_ml->ml_meth;

For built-in functions m_self is NULL so eq starts out true. We then compare the function pointers in ml_meth (the same posix_unlink referenced from the struct above) and since they match eq remains true. The end result is that python returns True.

The is operator is simpler and stricter. The is operator only compares the PyCFunctionObj* pointers. They will be different -- they came from different structs and are distinct objects, so the is operator will return False.

The rationale is likely that they are separate functions objects (recall their docstrings are different) but they point to the same implementation, so the difference in behavior between is and == is justifiable.

is brings a stronger guarantee, and is meant to be fast and cheap (a pointer comparison, essentially). The == operator inspects the object and returns True when its content matches. In this context, the function pointer is the content.

这篇关于在 Python (2.7) 中,为什么 os.remove 与 os.unlink 不同?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆