为什么要花时间访问被视为常量的非同类列表中的元素

时间:2013-09-24 14:07:13

标签: python python-2.7

为什么花时间访问被视为常量的非同类列表中的元素?如果是python,如何将非同类列表存储在内存中?

在同类列表的情况下,知道类型和位置,可以确定内存位置,但是如果非同类列表如此快速地将其视为恒定时间的函数,它是如何完成的?

浏览此页面Does Python use linked lists for lists? Why is inserting slow?我假设它将元素存储在连续的内存位置。

2 个答案:

答案 0 :(得分:3)

将列表视为对元素的引用数组。所有参考文献都有相同的大小;通过索引获取引用是恒定时间,并且取消引用它也是恒定时间。

答案 1 :(得分:3)

元组实际上是指向不同元素的指针数组。索引元组的索引是索引这个指针数组(O(1))并找到我们抓取的指针指向的位置(O(1))。

您可以在tupleobject.ctupleobject.h中自行查看。索引元组的代码是:

PyObject *
PyTuple_GetItem(PyObject *op, Py_ssize_t i)
{
    if (!PyTuple_Check(op)) {
        PyErr_BadInternalCall();
        return NULL;
    }
    if (i < 0 || i >= Py_SIZE(op)) {
        PyErr_SetString(PyExc_IndexError, "tuple index out of range");
        return NULL;
    }
    return ((PyTupleObject *)op) -> ob_item[i];
}

您可以看到最后一行索引底层C数组:ob_item[i](经过一些初步检查后)。 ob_item实际上是一个PyObject指针数组:

typedef struct {
    PyObject_VAR_HEAD
    PyObject *ob_item[1];

    /* ob_item contains space for 'ob_size' elements.
     * Items must normally not be NULL, except during construction when
     * the tuple is not yet visible outside the function that builds it.
     */
} PyTupleObject;