zoukankan      html  css  js  c++  java
  • 【源码】list

    前言

      本文探讨的Python版本为2.7.16,可从官网上下载,把压缩包Python-2.7.16.tgz解压到本地即可

      需要基本C语言的知识(要看的懂)

    PyListObject对象

    PyListObject对象可以有效地支持对元素的插入、添加、删除等操作,在Python的列表中,无一例外地存放的都是PyObject*指针

    [PyObject*,PyObject*,PyObject*]
    

    很显然,PyListObject一定是一个变长对象,因为不同的list中存储的元素个数会是不同的。但是,和PyStringObject不同的是,PyListObject对象还支持插入删除等操作,可以在运行时动态地调整其所维护的内存和元素,所以,它还是一个可变对象。

    首先看一下定义(文件Include/listobject.h):

    typedef struct {
        PyObject_VAR_HEAD
        /* Vector of pointers to list elements.  list[0] is ob_item[0], etc. */
        PyObject **ob_item;
    
        /* ob_item contains space for 'allocated' elements.  The number
         * currently in use is ob_size.
         * Invariants:
         *     0 <= ob_size <= allocated
         *     len(list) == ob_size
         *     ob_item == NULL implies ob_size == allocated == 0
         * list.sort() temporarily sets allocated to -1 to detect mutations.
         *
         * Items must normally not be NULL, except during construction when
         * the list is not yet visible outside the function that builds it.
         */
        Py_ssize_t allocated;
    } PyListObject; 

     其中关于PyObject_VAR_HEAD宏定义如下

    #define PyObject_VAR_HEAD               
        PyObject_HEAD                       
        Py_ssize_t ob_size; /* Number of items in variable part */
    
    #define PyObject_HEAD                   
        _PyObject_HEAD_EXTRA                
        Py_ssize_t ob_refcnt;               
        struct _typeobject *ob_type;

     上面代码可整理如下:

    typedef struct {
        Py_ssize_t ob_refcnt;               
        struct _typeobject *ob_type;
        Py_ssize_t ob_size;
        PyObject **ob_item;
        Py_ssize_t allocated;
    } PyListObject; 

    字段解释:

      ob_refcnt字段用来表示引用计数;指针ob_type指向_typeobject结构体,表明对象的类型。

    对应list对象而言,关键的是下面三个字段:

      ob_size 表示列表在使用的空间数量,**ob_item指向元素列表所在内存块的首地址,allocated中则维护了当前列表中的可容纳的元素(PyObject*)的总数。

    ob_size与allocated的区别:

      在每一次需要申请内存的时候,PyListObject总会申请一大块内存,这时申请的总内存的大小记录在allocated中,而其中实际被使用了的内存的数量则记录在了ob_size中。假如有一个能容纳10个元素的PyListObject对象已经装入了5个元素,那对于这个PyListObject对象,其ob_size为5,而allocated则为10。

    **ob_item为双重指针类型,指向了列表首地址,其中列表地址也是一个指针,真实数据存放于列表地址指向的内存地址当中,草图如下:

     

     

    摘自:《Python源码剖析》 — 陈儒

  • 相关阅读:
    GitLab的基础使用-汉化配置
    GitLab的基础使用-数据备份与恢复
    Apache Hadoop集群扩容实战案例
    Hadoop 集群-完全分布式模式(Fully-Distributed Mode)
    HDFS参数调优总结
    网站压力测试 工具webbench
    2013年十大必知的大数据分析公司
    做电子商务网上开店应该读的书
    教你用大功率路由器覆盖3平方公里的WiFi广告
    中央推进城镇化建设 六行业分享25万亿蛋糕
  • 原文地址:https://www.cnblogs.com/lianzhilei/p/11227510.html
Copyright © 2011-2022 走看看