浅谈对Python变量的一些认识理解
作者:软件技术学习开发爱好者 发布时间:2021-06-10 05:06:52
一、Python变量
在大多数语言中,为一个值起一个名字时,把这种行为称为“给变量赋值”或“把值存储在变量中”。不过,Python与许多其它计算机语言的有所不同,它并不是把值存储在变量中,而像是把名字“贴”在值的上边(专业一点说法是将名字绑定了对象)。所以,有些Python程序员会说Python没有变量,只有名字,通过名字找到它代表的值。
Python中的变量,与其它开发语言(如C语言)的不同:
在C语言中,变量类似于一个“容器”,赋给它的值,装在容器中:
定义一个变量 int a = 1;
给变量a重新赋值 a = 2;
把变量a赋值给另外一个变量b ,int b = a;
会重新创建一个变量b(容器),将a中的内容复制粘贴至b中。
在python中,变量类似于名字标签“贴”在值上面,通过名字找到它代表的值。
定义一个变量 a = 1
给变量a重新赋值 a = 2
把变量a赋值给另外一个变量b, b = a
创建新的便利贴b,与a同时贴到值上
为了对python中变量的这种情况加深认识,下面适度展开介绍。
1.1 第一点
先说明第一点:变量的实现方式有:引用语义、值语义
python语言中变量的实现方式就是引用语义,在变量里面保存的是值(对象)的引用(值所在处内存空间的地址)。采用这种方式,变量所需的存储空间大小一致,因为其中只需要保存一个引用。而有些语言(例如c)采用的不是这种方式,它们把变量直接保存在变量的存储区里,这种方式就称为值语义。这样的话,一个整数类型的变量就需要保存一个整数所需要的空间(例如c语言中int类型占用4个字节大小)。
python中变量与对象的引用关系类似于c语言的指针变量与指向地址之间的关系。
在python的数据结构中,对象分为可变对象和不可变对象。基本数据类型如int、float,元祖tuple、str是不可变对象;list(列表)、dict(字典)、set(集合)是可变对象,可变对象存储的元素的引用其实是没有改变的,改变的是其引用指向的值。
采用引用语义存储的只是一个变量的值所在的内存地址,而不是这个变量的值本身。
1.2 第二点
现在说明第二点:Python中的变量、对象、引用三者之间的关系。
在Python里一切皆对象。Python中,对象具有三要素:标识(identity)、类型(type)、值(value)。
☆标识(identity):
用于唯一标识对象,通常对应对象在计算机内存中的地址。使用内置函数id(obj)返回对象唯一标识。
☆类型(type):
类型可以限制对象的取值范围和可执行的操作。使用内置函数type(obj)返回对象所属类型。
对象中含有标准的头部信息:类型标识符。标识对象类型,表示对象存储的数据的类型。
每一个对象都有两个标准的头部信息:
1.类型标识符,去标识对象的(数据)类型;
2.引用计数器,记录当前对象的引用的数目。
(回收机制:变量的引用计数器为0,自动清理。 ※ 较小整数型对象有缓存机制。)
☆值(value):
表示对象存储的数据的信息。使用内置函数print(obj)可以直接打印值。
Python中,变量用来指向任意的对象,是对象的引用。Python变量更像是指针(或者说Python变量更像“贴签”),而不是数据存储区域(而不是数据“容器”)。
Python 中的变量不是装有对象的“容器”,而是贴在对象上的“标签”——给一个变量赋值,把这个标签贴到一个对象上,重新赋值,是撕下标签贴到另一个对象上。
在python中,变量保存的是对象(值)的引用,采用这种方式,变量的每一次初始化,都开辟了一个新的空间,将新内容的地址赋值给变量。id()函数可以获取变量在内存中的地址。我们把不同的值赋给变量时候,地址发生变化,相同的值地址不发生变化。下面给出示例:
【顺便提示:id()的值不是固定不变的——此值系统为对象分配的内存地址,在你练习时显示的不同值是正常的。】
下面是字符串的示例:
在Python中,值可以放在内存的某个位置(地址),变量用于引用它们,给变量赋一个新值,原值不会被新值覆盖,变量只是引用了新值。顺便说明,Python的垃圾回收机制会自动清理不再被用到的值,所以不用担心计算机内存中充满被“丢弃”的无效的值。
1.3 第三点
现在说明第三点:可变(mutable) 类型对象、不可变(immutable) 类型对象
可变类型对象,指对象可以在其 id() 保持固定的情况下改变其取值。
不可变类型对象,指具有固定值的对象。不可变对象包括数字(numbers)、字符串(strings)和元组(tuples)。这样的对象不能被改变。如果必须存储一个不同的值,则必须创建新的对象。不可变对象不允许对自身内容进行修改。如果我们对一个不可变对象进行赋值,实际上是生成一个新对象,再让变量指向这个对象。哪怕这个对象简单到只是数字 0 和 1。
由于 Python 中的变量存放的是对象引用,所以对于不可变对象而言,尽管对象本身不可变,但变量的对象引用是可变的。运用这样的机制,有时候会让人产生糊涂,似乎可变对象变化了。如下面的代码:
i = 73
i += 2
不可变的对象的特征没有变,依然是不可变对象,变的只是创建了新对象,改变了变量的对象引用。参见下图:
对于可变对象,其对象的内容是可以变化的。当对象的内容发生变化时,变量的对象引用是不会变化的。如下面的例子。
m=[5,9]
m+=[6]
参见下图:
二、总结
Python变量指的是名字绑定了对象(绑定就是将一个对象与一个名字联系起来)。
绑定时,变量就是名字。
使用时,变量代表对象的引用。
变量改变的只有绑定关系。
深入学习:
https://docs.python.org/zh-cn/3.9/reference/datamodel.html#objects-values-and-types
补充说明:
对复杂的数据类型(列表、集合、字典),如果添加某一项元素,或者添加几个元素,不会改变其本身的地址,只会改变其内部元素的地址引用,但是如果对其重新赋值时,就会重新赋予地址覆盖就地址,这时地址就会发生改变。示例代码如下:
list_ = [1,2,3,4]
print(list_, id(list_))
list_.append(5)
print(list_, id(list_))
#如上代码,因为append前后的list_仍然是同一个对象,只是对象的值发了改变,所以地址不变。
#再如下面的代码
print(list_, id(list_), id(list_[1]))#打印列表、列表的地址、第二个元素的地址
list_[1] = 'aaa' #修改列表
print(list_, id(list_), id(list_[1]))#打印列表、列表的地址、第二个元素的地址
#不难发发现:列表变了、列表的地址没有变、列表内部元素变了、列表内部元素的地址变了
测试运行如下图所示:
来源:https://blog.csdn.net/cnds123/article/details/116768499


猜你喜欢
- 可视化大屏适配/自适应现状可视化大屏的适配是一个老生常谈的话题了,现在其实不乏一些大佬开源的自适应插件、工具但是我为什么还要重复造轮子呢?因
- Linux服务器有CentOS、Fedora等,都预先安装了Python,版本从2.4到2.5不等,而Windows类型的服务器也多数安装了
- 开始制作符合标准的站点,第一件事情就是声明符合自己需要的DOCTYPE。查看本站首页原代码,可以看到第一行就是:<!DOCTYPE h
- 一、节点的定义dom节点树图中可见节点HTML文档中的每个成分都是一个节点:整个文档是一个文档节点每个HTML标签是一个元素节点包含在HTM
- 介绍也许大多数人都有在Excel中使用数据透视表的经历,其实Pandas也提供了一个类似的功能,名为pivot_table。虽然pivot_
- 1、主从同步原理主从同步架构图(异步同步)这是最常见的主从同步架构主从同步流程(异步同步)主库把数据变更写入binlog文件从库I/O线程发
- 前言pycharm可以很方便的管理Python的解释器(如果安装了多个的话),以及第三方模块,包。Pycharm是很多Python开发者的首
- 1 文件'''文件存储文件主名.扩展名'''Python中常有的数据文件类型有文本文件、二进
- 此类技巧还有很多,欢迎继续分享解析 URL从 James Padolsey 的 Blog中看到的个小技巧,就是利用 a 标签的 DOM 属性
- 先新建一组散点充当坐标轴为了比较直观地展示旋转过程,这里通过散点来新建三个坐标轴,通过对这三个坐标轴的转动,来直观地展现转动矩阵对坐标变换的
- TIMESTAMP类型返回日期时间数据中带有 T场景描述MySQL 中使用 TIMESTAMP 类型实体类使用 java.util.Date
- 首先是创建一个类,继承于ActionResult,记住要引用System.Web.Mvc命名空间,如下: public class Imag
- 最近刚好在学习python+scrapy的爬虫技术,因为mac是自带python2.7的,所以安装3.5版本有两种方法,一种是升级,一种是额
- [javascript] var forimg = function (foritem, hoverStop, defaultf
- 至此,我们的 Python零基础入门篇 的系列专栏到今天基本上算是结束了。今天没有任何的知识点,只是运用我们之前学习过的知识做两个小游戏的案
- 一、在windows环境下修改pip镜像源的方法(以python3.5为例)(1):在windows文件管理器中,输入 %APPDATA%(
- 光线追迹得益于计算机的计算的能力,通过追踪具有代表性的光线的传播轨迹,可以更加精确地描述光学系统的性能,光线追迹方法也因此大展其能,诸如Ze
- 关于PEP 8PEP 8,Style Guide forPythonCode,是Python官方推出编码约定,主要是为了保证 Python
- 本文实例讲述了MySQL学习笔记之创建、删除、修改表的方法。分享给大家供大家参考,具体如下:创建表:create table users(
- 开始现在要加速学习了,大佬们有没有内推,给个推荐会vue2/vue3 + ts断言非空断言非空断言就是确定这个变量不是null或者undef