python基础(9)增强型赋值与使用普通赋值的区别[通俗易懂]

python基础(9)增强型赋值与使用普通赋值的区别[通俗易懂]前言增强型赋值语句是经常被使用到的,因为从各种学习渠道中,我们能够得知i+=1的效率往往要比i=i+1更高一些(这里以+=为例,实际上增强型赋值语句不仅限于此)。所以我们会乐此不

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE使用 1年只要46元 售后保障 童叟无欺

前言

增强型赋值语句是经常被使用到的,因为从各种学习渠道中,我们能够得知i += 1的效率往往要比 i = i + 1 更高一些(这里以 += 为例,实际上增强型赋值语句不仅限于此)。所以我们会乐此不疲的在任何能够替换普通赋值语句的地方使用增量型赋值语句,以此来优化代码。那么我们是否有想过,在什么情况下 i += 1 其实并不等效于 i = i + 1 !!
 

增强型赋值语句:

>>> a = [1, 2, 3]
>>> b = a
>>> b += [4, 5, 6]
>>> a
[1, 2, 3, 4, 5, 6]
>>> b
[1, 2, 3, 4, 5, 6]
>>> id(a)
140268862690880
>>> id(b)
140268862690880
>>> 

代码解析:先定义了个列表a,然后创建对象b,b的地址指向a,所以a和b共用一片内存地址,b += [4, 5, 6]因为list是可变对象,所以b仍然在原来的内存地址上,只是改变了b的value,又因为a和b是指向同一地址的,所以a和b的值相等
 

普通赋值语句:

>>> a = [1, 2, 3]
>>> b = a
>>> b = b + [4, 5, 6]
>>> a
[1, 2, 3]
>>> b
[1, 2, 3, 4, 5, 6]
>>> id(a)
140268888586672
>>> id(b)
140268866910800
>>> 

代码解析:先定义了个列表a,然后创建对象b,b的地址指向a,目前a和b共用一片内存地址,关键点:b = b + [4, 5, 6],是在原来b的基础上,添加了一个列表,并且将新的值赋值给了左边的b,原先b的内存地址是指向a的,但是现在又重新赋值了,所以b重新开辟了一片新的内存地址,此时a和b的id和value均不同
 
python基础(9)增强型赋值与使用普通赋值的区别[通俗易懂]
这是一个值得注意的坑,警惕我们在使用增量赋值运算符来操作可变对象(如:列表)时可能会产生不可预测的结果。
 

增值运算符和普通运算符对于不可变对象作用一致

上面我们说的都是针对可变对象,但是针对不可变对象比如元组,他们都会产生新的内存地址

>>> a = (1, 2, 3)
>>> id(a)
140393063791584
>>> a += (4, )
>>> a
(1, 2, 3, 4)
>>> id(a)
140393063931056
>>> b = (1, 2, 3)
>>> id(b)
140393064025216
>>> b = b + (4, )
>>> b
(1, 2, 3, 4)
>>> id(b)
140393063930864
>>> 

 

总结

要解释这个问题,首先需要了解「Python 共享引用」的概念:在 Python 中,允许若干个不同的变量引用指向同一个内存对象。同时在前文中也提到,增强赋值语句比普通赋值语句的效率更高,这是因为在 Python 源码中, 增强赋值比普通赋值多实现了“写回”的功能,也就是说增强赋值在条件符合的情况下(例如:操作数是一个可变类型对象)会以追加的方式来进行处理,而普通赋值则会以新建的方式进行处理。这一特点导致了增强赋值语句中的变量对象始终只有一个,Python 解析器解析该语句时不会额外创建出新的内存对象。所以例一中变量 a、b 的引用在最后依旧指向了同一个内存对象;相反,对于普通赋值运算语句,Python 解析器无法分辨语句中的两个同名变量(例如:b = b + 1)是否应该为同一内存对象,所以干脆再创建出一个新的内存对象用来存放最后的运算结果,所以例二中的 a、b 从原来指向同一内存对象,到最后分别指向了两个不同的内存对象。
 
提示:尽量不要使用增量赋值运算符来处理任何可变类型对象,除非你对上述问题有了足够的了解。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/165486.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • 背句子,记单词1「建议收藏」

    背句子,记单词1「建议收藏」7000词汇这么背我比较可以接受,连续看20天足以过八级!!(16天完整版)16天记住7000考研词汇(第一天)1.WithmyownearsIclearlyheardtheheartbeatofthenuclearbomb.我亲耳清楚地听到原子弹的心脏的跳动。2.Nextyearthebeardedbearwillbear…

    2022年8月24日
    3
  • Ubuntu 安装使用yum[通俗易懂]

    Ubuntu 安装使用yum[通俗易懂]第一步:安装 build-essential 软件包  先简要说明一下这个包的作用,    Ubuntu缺省情况下,并没有提供C/C++的编译环境,因此还需要手动安装。如果单独安装gcc以及g++比较麻烦,幸运的是,为了能够编译Ubuntu的内核,Ubuntu提供了一个build-essential软件包。查看该软件包的依赖关系,可以看到以下内容:$apt-…

    2022年6月28日
    71
  • linux lefse分析,科学网-linux本地化进行lefse分析-林国鹏的博文

    linux lefse分析,科学网-linux本地化进行lefse分析-林国鹏的博文注:参考来自网络,如侵权则删。##对应于上述A-F6个模块,本地版的命令行操作示例如下#A,设置LEfSe的数据格式,详情format_input.py-h#-c,指定class的行(必须指定);-s,指定sub_class的行(可缺省);#-u,指定subject_id的行(可缺省);-o,设置归一化值,默认-1即不执行标准化#注:版本问题,有时format_in…

    2022年4月29日
    50
  • 详解 MNIST 数据集

    MNIST数据集已经是一个被”嚼烂”了的数据集,很多教程都会对它”下手”,几乎成为一个“典范”.不过有些人可能对它还不是很了解,下面来介绍一下.MNIST数据集可在http://yann.lecun.com/exdb/mnist/获取,它包含了四个部分:Trainingsetimages:train-images-idx3-ubyte.gz(9.9MB,解压后47

    2022年4月6日
    280
  • C++字符串加密_c++字符串连接函数

    C++字符串加密_c++字符串连接函数有的时候,使用C++进行爬虫操作时,会涉及到一些请求参数的加密,例如对utf8的中文进行加密,我们用js对如下字符串进行加密的结果如下:加密前字符串:keras-lx-还魂草.z01URL加密后:keras-lx-%E8%BF%98%E9%AD%82%E8%8D%89.z01使用网页在线加密工具和使用js加密效果是一样的自己用C++写的URL加密代码如下://URL编码.cpp:…

    2022年10月28日
    0
  • pycharm使用技巧及常用快捷键_全屏快捷键

    pycharm使用技巧及常用快捷键_全屏快捷键Pycharm常用快捷键1、编辑(Editing)Ctrl+Space基本的代码完成(类、方法、属性)Ctrl+Alt+Space快速导入任意类Ctrl+Shift+Enter语句完成Ctrl+P参数信息(在方法中调用参数)Ctrl+Q快速查看文档F1外部文档Shift+F1外部文档,进入web文档主页Ctrl+Shift+Z–>Redo重做Ctrl+鼠标简介/进入代码定义Ctrl+F1显示错误描述或警告.

    2022年8月26日
    3

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号