美文网首页初入python
内存简析(上)

内存简析(上)

作者: 言烬 | 来源:发表于2018-08-23 20:38 被阅读0次

    程序在运行需要将数据加载到内存中,然后通过CPU进行内存数据的读写完成数据的运算。

    内存浅析:

    软件程序在程序中的执行,主要是通过数据单元、控制单元、执行单元共同协作,完成数据的交互,达到程序处理数据的目的。

    在软件执行的过程,由于系统内存和CPU的资源非常有限,所以有效的分解软件中的各项数据,将不同数据加载到不同的内存部分以有效的运行程序,同时可以达到在计算机中有效的运行更多软件的目的。

    持久化:在一个可以永久存储数据的地方进行数据的读取和存储

    图解:

    图片1.png

    python程序在运行的过程中主要是解释器从系统中申请内存空间以运行python软件。

    python解释器将申请到的内存主要分成四个部分:

    栈内存区(stack)、堆内存区(heap)、静态区|常量区(static)、方法区|数据区(data)

    栈内存区:用于直接分配数据,存取速度较快,数据存储不稳定,适合用于小数据块的快速存取,常用于存储“变量”

    堆内存区:用于加载程序中使用的代码数据,二进制数据,方法数据等等程序运行需要的预加载数据,存取速度较慢,比较消耗资源,但只要数据存在,数据操作比较稳定。常用于存储“对象”

    静态储存区|常量区:专门存放程序中的公共数据,静态数据的内存区域

    方法区|数据区:专门加载程序运行的代码字节数据,方法数据,函数数据等等

    图解:

    图片2.png

    内存分配基础代码:


    图片7.png

    图解代码:

    图片3.png

    不可变数据类型与可变数据类型

    python中根据数据是否可以进行修改提供了两种不同的数据类型

    不可变数据类型:一般基本数据类型都是不可变数据类型,对象在内存地址中存储的数据可变。例如:b = 12

    整数类型:-5 ~ 255在解释器加载时,常量区已经自动分配好了这些数字的内存地址

    超出这个数字的范围,在一个代码块中申请一次内存

    交互模式下一行代码就是一个代码块

    开发工具下一个模块就是一个代码块

    不可变类型在同一个代码块中进行多次使用时,会将该类型的对象,直接创建在常量区,在任意引用的时候直接赋值内存地址,因为不可变类型的对象数据不会发生变化,所以内存中存储一份即可!用于优化程序执行效率

    可变数据类型:一般组合数据类型或者自定义数据类型都是可变数据类型,对象在内存地址中存储的数据不可变。例如:a = list()

    一般情况下,可变类型的对象会直接创建在堆内存中

    不可变类型的对象会创建在常量区内存中

    关于字符串:因为字符串使用的频率较高,为了提高程序运行效率,会优先优化字符串

    如果要创建一个字符串对象,程序会先到常量区里寻找这个字符串,如果常量区里存在这个字符串,直接取出来赋值给变量。如果没有,创建一个赋值给变量,这样在下一次使用的时候,程序先在常量区里寻找,然后直接赋值。这个字符串对象不会删除

    思考题:

    # 思考题:
    nums = [12, 13, 15, 18, 20, "hello", ["world", "python"]]
    
    a = 20  #  nums[4] 是否同一个内存地址? 是!
    print(id(a), id(nums[4]))
    
    b = "hello"# nums[5] 是否同一个内存地址?是
    print(id(b), id(nums[5]))
    
    c = ["world", "python"] # nums[6] 是否同一个内存地址 否
    print(id(c), id(nums[6]))
    
    print(id(nums[6][0]), id(c[0])) # 两个列表中的world字符串 是
    

    试题:

    # 奇怪的语法
    if [1][0]:
        print("hello")
    else:
        print("world")
    

    解释:这个语法中,[1]是一个列表,[0]代表的是索引,1代表True,所以输出hello

    精确控制数据:

    试题:

    def chg_nums(n):
        n = 20
    
    
    def chg_list(l):
        l.append(20)
    
    
    a = 18
    chg_nums(a)
    
    b = [1,2]
    chg_list(b)
    
    print(a) # ?18        20                18             20
    print(b) # ?[1,2]     [1,2,20]          [1,2,20]       [1,2]
    

    输出结果:

    图片6.png

    解释:a,n原本都等于18,经过函数chg_nums(),n被赋值为20,但a仍然是18,所以a仍然等于18。

    b是一个列表[1,2], 经过调用函数chg_list(), 出现一个新的变量l, l仍指向列表[1,2], 因为函数中l增加了一个数字20,所以l变成了[1,2,20], 即列表变成了[1,2,20],所以b输出[1,2,20]

    图片4.png 图片5.png

    如有错误,敬请指出

    相关文章

      网友评论

        本文标题:内存简析(上)

        本文链接:https://www.haomeiwen.com/subject/myamiftx.html