关于python变量的引用以及在底层存储原理

 更新时间:2021年09月18日 11:46:47   作者:涤生手记  
Python的变量,简单来说有数值型,布尔型,字符串类型,列表,元组,字典等6大类。那么不同变量类型在底层是如何存储的,关系到变量的引用,能否正确的掌握变量的相关操作?接下来小编就来为大家讲解python变量的引用以及在底层存储原理,需要的朋友可以参考一下

Python的变量,简单来说有数值型,布尔型,字符串类型,列表,元组,字典等6大类。那么不同变量类型在底层是如何存储的,关系到变量的引用,能否正确的掌握变量的相关操作

下面v1,v2的值分别是多少?为什么?

v1 =3
v2=v1
print("v2:",v2)
v1 += 2
print("v1:",v1)
print("v2:",v2)
 


#下面l2的值又是多少?为什么?

l1 = [1,2,3]
l2 =l1
print(l2)
l1.append(4)
print(l2)


1.变量的引用的底层原理

v1 =3
v2=v1            
print("v2:",v2)
v1 += 2          
print("v1:",v1)  
print("v2:",v2)   #v1的值变化了,为什么v2的值没有跟着变化呢?
'''


执行结果如下:

v1: 5
v2: 3
'''

l1 = [1,2,3]
l2 =l1
print(l2)
l1.append(4)
print(l2)    #l1的值变化了,但是为什么l2的值也跟着变化了。
'''

执行结果如下:

[1, 2, 3]
[1, 2, 3, 4]

'''

要点分析:

  • 可变对象和不可变对象:不可变对象包括intfloatstringtuple等。可变对象包括list,dict,自定义类的实例等。
  • python中通过= 复制的变量,都是同时即把变量的值,也把变量在内存中的地址复制也过去了。即=复制过的变量不仅内存地址一样,变量的值也一样。但是需要注意的是:对于不可变类型(如int)的变量,如果要更改变量的值,则会创建一个新值,并且给这个新值分配一个新的内存地址,然后把变量指向这个新值的内存地址上,而旧值如果没有被引用就等待垃圾回收。如果是可变类型变量。如果修改变量的值,则可以直接修改变量的值,变量的引用地址不会变。

不可变类型:变量赋值 a=5 后再赋值 a=10,这里实际是新生成一个 int 值对象 10,再让 a 指向它,而 5 被丢弃,不是改变a的值,相当于新生成了a。

可变类型:变量赋值 la=[1,2,3,4] 后再赋值 la[2]=5 则是将 list la 的第三个元素值更改,本身la没有动,只是其内部的一部分值被修改了。

  • 本质是因为不可变对象一旦新建后,系统就会根据他的大小给他分配固定死的内存,所以不允许修改,只修改值只能申请新的内存和地址。而可变对象,他的内存大小可以随着值的变化而自动扩容    

代码分析演示:

因为变量在内存中新建时,系统都会给他分配一个地址,然后通过地址去查找或引用他的值。  Python的所有变量其实都是指向内存中的对象的一个指针,都是值的引用

代码演示1:

v1 =3
v2=v1
print("v1在内存的地址:%d,v2在内存中地址:%d"%(id(v1),id(v2)))
v1 += 2
print("v1在内存的地址:%d,v2在内存中地址:%d"%(id(v1),id(v2)))
print("v1:",v1)
print("v2:",v2)
========================================================
v1在内存的地址:1747378992,v2在内存中地址:1747378992
v1在内存的地址:1747379024,v2在内存中地址:1747378992
v1: 5
v2: 3
'''


因为:v1,v2都是int,为不可变对象,所以一旦修改他们的值,包扣加减乘除赋值等操作,系统会在内存中给他们重新创建一个。
然后再把这个变量绑定(通过地址引用)到这个值上,所以v1 +=2后,他在内存中的地址变了。而v2依旧引用的是之前的地址,所以v2的值
没有更新。
'''

代码演示2:

l1 = [1,2,3]
l2 =l1
print("l1在内存的地址:%d,l2在内存中地址:%d"%(id(l1),id(l2)))
print(l2)
print("l1在内存的地址:%d,l2在内存中地址:%d"%(id(l1),id(l2)))
l1.append(4)
print(l2)
print("l1在内存的地址:%d"%(id(l1)))
=======================================================
l1在内存的地址:37345880,l2在内存中地址:37345880
[1, 2, 3]
l1在内存的地址:37345880,l2在内存中地址:37345880
[1, 2, 3, 4]
l1在内存的地址:37345880

对于可变对象如列表,l1,l2,当修改他们的值时,系统会自动在原地址上给他们扩容内存,所以不用修改地址。

代码演示3:同理字符串等不可变的变量引用效果也一样。

str1 ='hahhahah'
str2 = str1
str1 += "123"
print(str1,str2)
hahhahah123 hahhahah

2.变量的分类

可变类型与不可变类型

可变类型,值可以改变:

  • 列表 list
  • 字典 dict

不可变类型,值不可以改变:

  • 数值类型 int, long, bool, float
  • 字符串 str
  • 元组 tuple

到此这篇关于关于python变量的引用以及在底层存储原理的文章就介绍到这了,更多相关python变量的引用以及在底层存储原理内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • python打开文件的方式有哪些

    python打开文件的方式有哪些

    在本篇文章里小编给大家分享了关于python打开文件的方式,需要的朋友们可以学习参考下。
    2020-06-06
  • Python 的字典(Dict)是如何存储的

    Python 的字典(Dict)是如何存储的

    这篇文章主要介绍了Python 的字典(Dict)是如何存储的,文中介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2019-07-07
  • 基于深度学习和OpenCV实现目标检测

    基于深度学习和OpenCV实现目标检测

    这篇文章主要介绍了通过使用OpenCV进行基于深度学习的对象检测以及使用OpenCV检测视频,文中的示例代码讲解详细,需要的可以参考一下
    2021-12-12
  • Python实现Linux中的du命令

    Python实现Linux中的du命令

    这篇文章主要介绍了Python实现Linux中简单du命令,需要的朋友可以参考下
    2017-06-06
  • python 实现数字字符串左侧补零的方法

    python 实现数字字符串左侧补零的方法

    今天小编就为大家分享一篇python 实现数字字符串左侧补零的方法,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2018-12-12
  • python常见数制转换实例分析

    python常见数制转换实例分析

    这篇文章主要介绍了python常见数制转换,实例分析了二进制、八进制、十进制及十六进制之间的相互转换技巧,需要的朋友可以参考下
    2015-05-05
  • Python绘制热力图示例

    Python绘制热力图示例

    这篇文章主要介绍了Python绘制热力图,结合实例形式分析了Python使用pyheatmap及matplotlib模块进行数值计算与图形绘制相关操作技巧,需要的朋友可以参考下
    2019-09-09
  • 如何利用python实现图片转化字符画

    如何利用python实现图片转化字符画

    这篇文章主要介绍了如何利用python实现图片转化字符画,文章围绕主题展开详细的内容介绍,具有一定的参考价值,需要的小伙伴可以参考一下
    2022-06-06
  • Pycharm打开已有项目配置python环境的方法

    Pycharm打开已有项目配置python环境的方法

    这篇文章主要介绍了Pycharm打开已有项目配置python环境的方法,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-07-07
  • python Kmeans算法原理深入解析

    python Kmeans算法原理深入解析

    这篇文章主要介绍了python Kmeans算法深入解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2019-08-08

最新评论