Get started
The document https://docs.python.org/3.8/reference/expressions.html#is-not means that for x is y
it is true if and only if the two variables point to the same object. The object can use the id()
function to check its identity (the id()
function returns the mapping of the object in memory).
bytecode of is and is not
is
and is not
are both operators. is not
is the whole, don't take x is not y
as x is (not y)
.
Let's take a look at the bytecodes corresponding to these two operators (based on Python 3.8):
>>> def fun():
... x is y
... x is not y
...
>>> import dis
>>> dis.dis(fun)
2 0 LOAD_GLOBAL 0 (x)
2 LOAD_GLOBAL 1 (y)
4 COMPARE_OP 8 (is)
6 POP_TOP
3 8 LOAD_GLOBAL 0 (x)
10 LOAD_GLOBAL 1 (y)
12 COMPARE_OP 9 (is not)
14 POP_TOP
16 LOAD_CONST 0 (None)
18 RETURN_VALUE
>>>
For COMPARE_OP
corresponding actions
case TARGET(COMPARE_OP): {
PyObject *right = POP();
PyObject *left = TOP();
PyObject *res = cmp_outcome(tstate, oparg, left, right);
Py_DECREF(left);
Py_DECREF(right);
SET_TOP(res);
if (res == NULL)
goto error;
PREDICT(POP_JUMP_IF_FALSE);
PREDICT(POP_JUMP_IF_TRUE);
DISPATCH();
}
The meaning of this part of the code is to first take the two operands of the generation comparison from the stack, get the result of the two-number operation cmp_outcome(tstate, oparg, left, right)
res
top of the stack.
The relevant code of the cmp_outcome
static PyObject *
cmp_outcome(PyThreadState *tstate, int op, PyObject *v, PyObject *w)
{
int res = 0;
switch (op) {
case PyCmp_IS:
res = (v == w);
break;
case PyCmp_IS_NOT:
res = (v != w);
break;
...
}
v = res ? Py_True : Py_False;
Py_INCREF(v);
return v;
}
In the cmp_outcome()
function, only by comparing whether the values of the two pointers are equal to determine whether they point to the same object.
Pure Python code explanation
The id()
function can be used to determine the corresponding address of an object in memory, so it can also be used to determine whether two variables point to the same object:
def _is(a, b):
return id(a) == id(b)
def _is_not(a, b):
return id(a) != id(b)
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。