您好, 欢迎来到 !    登录 | 注册 | | 设为首页 | 收藏本站

为什么Python的数组变慢?

为什么Python的数组变慢?

存储 是“未装箱的”,但是每次访问元素时,Python都必须对其进行“装箱”(将其嵌入常规Python对象中)以便对其进行任何处理。例如,您sum(A)遍历数组,并将每个整数一次装在一个常规Pythonint对象中。那要花时间。在中sum(L),所有装箱操作均在创建列表时完成。

因此,最后,阵列通常较慢,但所需的内存却少得多。

这是最新版本的Python 3的相关代码,但是自Python首次发布以来,相同的基本思想也适用于所有cpython实现。

这是访问列表项的代码

PyObject *
PyList_GetItem(PyObject *op, Py_ssize_t i)
{
    /* error checking omitted */
    return ((PyListObject *)op) -> ob_item[i];
}

它几乎没有什么:somelist[i]只返回i列表中的第一个对象(并且cpython中的所有Python对象都是指向结构的指针,该结构的初始段符合的布局struct PyObject)。

__getitem__array带有类型代码的实现l

static PyObject *
l_getitem(arrayobject *ap, Py_ssize_t i)
{
    return PyLong_FromLong(((long *)ap->ob_item)[i]);
}

原始内存被视为平台本地C long整数的矢量;该i“个C long被读取起来; 然后PyLong_FromLong()调用方法将本机包装(“框”)C long在Pythonlong对象中(在Python 3中,该对象消除了Python 2int和之间的区别long,实际上显示为type int)。

这种装箱必须为Pythonint对象分配新的内存,然后将nativeC long的位喷射到其中。在原始示例的上下文中,此对象的生存期非常短(足够长,足以sum()内容添加到正在运行的总计中),然后需要更多的时间来取消分配新int对象。

这就是速度差异的来源,在cpython实现中,总是如此,而且总是如此。

python 2022/1/1 18:27:15 有194人围观

撰写回答


你尚未登录,登录后可以

和开发者交流问题的细节

关注并接收问题和回答的更新提醒

参与内容的编辑和改进,让解决方法与时俱进

请先登录

推荐问题


联系我
置顶