代码之家  ›  专栏  ›  技术社区  ›  LeMiz

Python结构的内存大小

  •  102
  • LeMiz  · 技术社区  · 17 年前

    32位和64位平台上Python数据结构的内存大小是否有参考?

    如果不是的话,穿上它就好了。越详尽越好!那么以下Python结构使用了多少字节(取决于 len

    • int
    • float
    • 参考
    • str
    • tuple
    • list
    • dict
    • set
    • array.array
    • numpy.array
    • deque
    • 新型类对象
    • 旧式类对象

    (对于只保留对其他对象的引用的容器,我们显然不想计算项目本身的大小,因为它可能是共享的。)

    此外,是否有一种方法可以获取对象在运行时使用的内存(递归还是非递归)?

    6 回复  |  直到 11 年前
        1
  •  155
  •   Community Mohan Dere    9 年前

    委员会的建议 an earlier question 在这一点上是要使用的 sys.getsizeof() ,引述:

    >>> import sys
    >>> x = 2
    >>> sys.getsizeof(x)
    14
    >>> sys.getsizeof(sys.getsizeof)
    32
    >>> sys.getsizeof('this')
    38
    >>> sys.getsizeof('this also')
    48
    

    您可以采取以下方法:

    >>> import sys
    >>> import decimal
    >>> 
    >>> d = {
    ...     "int": 0,
    ...     "float": 0.0,
    ...     "dict": dict(),
    ...     "set": set(),
    ...     "tuple": tuple(),
    ...     "list": list(),
    ...     "str": "a",
    ...     "unicode": u"a",
    ...     "decimal": decimal.Decimal(0),
    ...     "object": object(),
    ... }
    >>> for k, v in sorted(d.iteritems()):
    ...     print k, sys.getsizeof(v)
    ...
    decimal 40
    dict 140
    float 16
    int 12
    list 36
    object 8
    set 116
    str 25
    tuple 28
    unicode 28
    

    2012-09-30

    python 2.7(linux,32位):

    decimal 36
    dict 136
    float 16
    int 12
    list 32
    object 8
    set 112
    str 22
    tuple 24
    unicode 32
    

    decimal 52
    dict 144
    float 16
    int 14
    list 32
    object 8
    set 112
    str 26
    tuple 24
    unicode 26
    

    2016-08-01

    decimal 80
    dict 280
    float 24
    int 24
    list 72
    object 16
    set 232
    str 38
    tuple 56
    unicode 52
    
        2
  •  43
  •   Kobold    9 年前

    这里有一个很好的答案: https://goshippo.com/blog/measure-real-size-any-python-object/

    关键点是:

    import sys
    
    def get_size(obj, seen=None):
        """Recursively finds size of objects"""
        size = sys.getsizeof(obj)
        if seen is None:
            seen = set()
        obj_id = id(obj)
        if obj_id in seen:
            return 0
        # Important mark as seen *before* entering recursion to gracefully handle
        # self-referential objects
        seen.add(obj_id)
        if isinstance(obj, dict):
            size += sum([get_size(v, seen) for v in obj.values()])
            size += sum([get_size(k, seen) for k in obj.keys()])
        elif hasattr(obj, '__dict__'):
            size += get_size(obj.__dict__, seen)
        elif hasattr(obj, '__iter__') and not isinstance(obj, (str, bytes, bytearray)):
            size += sum([get_size(i, seen) for i in obj])
        return size
    

    这样使用:

    In [1]: get_size(1)
    Out[1]: 24
    
    In [2]: get_size([1])
    Out[2]: 104
    
    In [3]: get_size([[1]])
    Out[3]: 184
    

    如果您想更深入地了解Python的内存模型,这里有一篇很棒的文章,其中有一段类似的“总大小”代码片段,作为较长解释的一部分: https://code.tutsplus.com/tutorials/understand-how-much-memory-your-python-objects-use--cms-25609

        3
  •  39
  •   Joël Brigate Peter Brittain    5 年前

    我一直很高兴使用它 pympler 对于这样的任务。它与许多版本的Python兼容 asizeof

    例如,使用hughdbrown的示例,但是 from pympler import asizeof print asizeof.asizeof(v) 最后,我看到了(MacOSX 10.5上的系统Python 2.5):

    $ python pymp.py 
    set 120
    unicode 32
    tuple 32
    int 16
    decimal 152
    float 16
    list 40
    object 0
    dict 144
    str 32
    

        4
  •  9
  •   Tampa    14 年前

    试试内存分析器。 memory profiler

    Line #    Mem usage  Increment   Line Contents
    ==============================================
         3                           @profile
         4      5.97 MB    0.00 MB   def my_func():
         5     13.61 MB    7.64 MB       a = [1] * (10 ** 6)
         6    166.20 MB  152.59 MB       b = [2] * (2 * 10 ** 7)
         7     13.61 MB -152.59 MB       del b
         8     13.61 MB    0.00 MB       return a
    
        5
  •  7
  •   Omid Raha    12 年前

    guppy 单元

    >>> from guppy import hpy; hp=hpy()
    >>> hp.heap()
    Partition of a set of 25853 objects. Total size = 3320992 bytes.
     Index  Count   %     Size   % Cumulative  % Kind (class / dict of class)
         0  11731  45   929072  28    929072  28 str
         1   5832  23   469760  14   1398832  42 tuple
         2    324   1   277728   8   1676560  50 dict (no owner)
         3     70   0   216976   7   1893536  57 dict of module
         4    199   1   210856   6   2104392  63 dict of type
         5   1627   6   208256   6   2312648  70 types.CodeType
         6   1592   6   191040   6   2503688  75 function
         7    199   1   177008   5   2680696  81 type
         8    124   0   135328   4   2816024  85 dict of class
         9   1045   4    83600   3   2899624  87 __builtin__.wrapper_descriptor
    <90 more rows. Type e.g. '_.more' to view.>
    

    以及:

    >>> hp.iso(1, [1], "1", (1,), {1:1}, None)
    Partition of a set of 6 objects. Total size = 560 bytes.
     Index  Count   %     Size   % Cumulative  % Kind (class / dict of class)
         0      1  17      280  50       280  50 dict (no owner)
         1      1  17      136  24       416  74 list
         2      1  17       64  11       480  86 tuple
         3      1  17       40   7       520  93 str
         4      1  17       24   4       544  97 int
         5      1  17       16   3       560 100 types.NoneType
    
        6
  •  0
  •   zahypeti    6 年前

    你也可以利用 tracemalloc

        7
  •  -1
  •   B--rian Optider    6 年前

    当你使用 dir([object]) 内置函数,可以获得 __sizeof__

    >>> a = -1
    >>> a.__sizeof__()
    24