python变量赋值方法(可变与不可变)

python中不存在所谓的传值调用,一切传递的都是对象的引用,也可以认为是传址。

一、可变对象和不可变对象

Python在heap中分配的对象分成两类:可变对象和不可变对象。所谓可变对象是指,对象的内容可变,而不可变对象是指对象内容不可变。

不可变(immutable):int、字符串(string)、float、(数值型number)、元组(tuple)

可变(mutable):字典型(dictionary)、列表型(list)

不可变类型特点:

看下面的例子(例1)

i = 73
i += 2

从上图可知,不可变对象的特征没有变,变的只是创建了新对象,改变了变量的对象引用。

看一个例子(例2)   

>>>x = 1
>>>y = 1
>>>z = 1
>>> x is y
True
>>>y is z
True

如上所示,因为整数为不可变,x,y,z在内存中均指向一个值为1的内存地址,也就是说,x,y,z均指向的是同一个地址,值得注意的是,整形来说,目前仅支持(-1,100)。

总结一下,不可变对象的优缺点。

优点是,这样可以减少重复的值对内存空间的占用。

缺点呢,如例1所示,我要修改这个变量绑定的值,如果内存中没用存在该值的内存块,那么必须重新开辟一块内存,把新地址与变量名绑定。而不是修改变量原来指向的内存块的值,这回给执行效率带来一定的降低。

下面看一个可变对象的例子(例3)   

m=[5,9]
m+=[6]

二、函数参数:

Python函数参数对于可变对象,函数内对参数的改变会影响到原始对象;对于不可变对象,函数内对参数的改变不会影响到原始参数。原因在于:

1、可变对象,参数改变的是可变对象,其内容可以被修改。

2、不可变对象,改变的是函数内变量的指向对象。

比如存在2个列表 a 和 b

如果a=b的话, a和b的地址是相同的;如果只是想拷贝,那么就得用 a=b[:]

def mutable(b = []): #函数使用了缺省变量
  b.append(0)
  return b
>>>mutable()
[0]
>>>mutable()
[0,0]
>>>mutable()
[0,0,0]

这里连续三次以缺省值,运行函数3此,每次的结果都不一样,按我们的想想,三次的结果,应该是一样的,都为[0],但是…

那么原因是什么呢,前面说过,一切皆为对象,函数mutable也为一个对象,使用dir()查看函数的属性:

dir(mutable)

['__annotations__', '__call__', '__class__', '__closure__', '__code__', '__defaults__', '__delattr__', '__dict__', '__doc__', '__eq__', '__format__', '__ge__', '__get__', '__getattribute__', '__globals__', '__gt__', '__hash__', '__init__', '__kwdefaults__', '__le__', '__lt__', '__module__', '__name__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__',

上面我们三次运行了mutable这个函数,如果用mutable.__defaults__来查看函数对象的默认参数变化的话,就会发现问题了。

>>>mutable.__defaults__
([],)
>>>mutable()
[0]
>>>mutable.__defaults__
([0],)
>>>mutable()
[0,0]
>>>mutable.__defaults__
([0,0],)

仔细观察,类对象内部属性dict中'x'对应的值,在每创建一个对象时都发生了变化。也就是说,在每次创建类对象时,变量x引用内存的初始值是不同的,这终要归因于列表(list)的可变性导致的。每次创建对象时,因为列表的可变性,函数对象b的dict属性中,x键对应的值,被改变,而不是重新创建,所以出现了上面的结果。

综上:初学者如果不充分理解python的变量和类型和参数传递方式,或者是一切解释对象的原理,会很容易产生上面的错误。

以上这篇python变量赋值方法(可变与不可变)就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持我们。

(0)

相关推荐

  • 浅谈Python 列表字典赋值的陷阱

    今天在用python刷leetcode 3Sum problem时,调入到了一个大坑中,检查半天并没有任何逻辑错误,但输出结果却总是不对,最终通过调试发现原来python中list和dict类型直接赋值竟然是浅拷贝!!!因此,在实际实验中,若要实现深拷贝,建立新list或dict,使新建的list或dict变量和以前的变量只是具有相同的值,但是却具有不同的存储地址,保证在改变以前的list变量的时候,不会对新的list产生任何影响. python中的深拷贝的实现需要通过copy.deepcopy

  • python 解决动态的定义变量名,并给其赋值的方法(大数据处理)

    最近消费kafka数据到磁盘的时候遇到了这样的问题: 需求:每天大概有1千万条数据,每条数据包含19个字段信息,需要将数据写到服务器磁盘,以第二个字段作为大类建立目录,第7个字段作为小类配合时间戳作为文件名,临时文件后缀tmp,当每个文件的写入条数(可配置,比如100条)达到要求条数时,将后缀tmp改为out. 问题:大类共有30个,小类不计其数而且未知,比如大类为A,小类为a,时间戳为20180606095835234,则A目录下的文件名为20180606095835234_a.tmp,这样一

  • Python动态赋值的陷阱知识点总结

    忘了在哪看到一位编程大牛调侃,他说程序员每天就做两件事,其中之一就是处理字符串.相信不少同学会有同感. 几乎任何一种编程语言,都把字符串列为最基础和不可或缺的数据类型.而拼接字符串是必备的一种技能.今天,我跟大家一起来学习Python拼接字符串的七种方式. 1.来自C语言的%方式 print('%s %s' % ('Hello', 'world')) >>> Hello world %号格式化字符串的方式继承自古老的C语言,这在很多编程语言都有类似的实现.上例的%s是一个占位符,它仅代表

  • python批量赋值操作实例

    变量名和变量值俊发生规律的变化,利用for循环完成赋值操作. 举个例子: for i in range(1, 10): exec("t%d=i"%i) print(t1) print(t2) print(t3) print(t4) print(t5) print(t6) print(t7) print(t8) print(t9) 执行结果: 1 2 3 4 5 6 7 8 9 利用python中的exec()函数来完成. 以上这篇python批量赋值操作实例就是小编分享给大家的全部内容

  • 解决python字典对值(值为列表)赋值出现重复的问题

    可能很少有人遇到这个问题,网上也没找到,这里记录一下,希望也可以帮到其他人. 问题描述:假设有一个字典data,其键不定,可能随时添加键(这不是关键),某一个键下面对应的值为一个长度为10的list,初始化为0,然后我想修改某些键下面的列表中的某一个值,比如data有一个键'k',对应的值为[0,0,0,0,0,0,0,0,0,0],现在我想把键'k'对应的列表的第三个数改成3,即[0,0,3,0,0,0,0,0,0,0],可是意外的事情发生了,如果data还有一个键'k1',假设其值为[0,0

  • Python创建一个空的dataframe,并循环赋值的方法

    如下所示: # 创建一个空的 DataFrame df_empty = pd.DataFrame() #或者 df_empty = pd.DataFrame(columns=['A', 'B', 'C', 'D']) #添加数据 a为一个新的dataframe df_empty = df_empty.append(a) 以上这篇Python创建一个空的dataframe,并循环赋值的方法就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持我们.

  • 浅谈python连续赋值可能引发的错误

    今天写的代码片段: X = Y = [] .. X.append(x) Y.append(y) 其中x和y是读取的每一个数据的xy值,打算将其归入列表之后绘散点图,但是绘图出来却是一条直线,数据本身并不是这样分布的. 反复检查后,发现是X = Y =[]这一句的错误. 在python中,形如X = Y的拷贝都是浅拷贝,X和Y是公用同一块空间的,一旦对它们其中的任意一个进行数据操作,都会改变该空间的内容,除非重新赋一块空间,改变其指向的位置. 因此只需要改成: X = [] Y = [] 就可以运

  • python变量赋值方法(可变与不可变)

    python中不存在所谓的传值调用,一切传递的都是对象的引用,也可以认为是传址. 一.可变对象和不可变对象 Python在heap中分配的对象分成两类:可变对象和不可变对象.所谓可变对象是指,对象的内容可变,而不可变对象是指对象内容不可变. 不可变(immutable):int.字符串(string).float.(数值型number).元组(tuple) 可变(mutable):字典型(dictionary).列表型(list) 不可变类型特点: 看下面的例子(例1) i = 73 i +=

  • python变量赋值机制踩坑记录

    目录 1.可变类型赋值 2.不可变类型赋值 3.自定义类型变量赋值 先说结论: 变量赋值属于浅拷贝(关于深拷贝和浅拷贝的区别可以自己了解下).故如果是可变类型变量(如a是list类型,a=b)赋值,修改a会牵连到b:如果是不可变类型(如int)的赋值,则修改任意变量不会传递. 1. 可变类型赋值 可以看出,对于可变类型赋值,变量始终指向同一块地址. 2. 不可变类型赋值 对于不可变类型变量的赋值,刚开始是指向同一块地址,但修改任意变量,则修改的变量指向另外一块地址,不会影响另外一个变量. 那么问

  • Python变量赋值的秘密分享

    在Python中,我们令一个变量等于另外一个变量时,并不是把值传递给它,而是直接把指向的地址更改了.我们想要查看一个变量在内存中的地址,可以通过id(变量) 来查看.我们通过一个小例子来看看这个有趣的过程. >>> x = 12 >>> y= 13 >>> id(x) >>> id(y) >>> x = y >>> id(x) >>> id(y) 首先给x变量赋值为12,y变量赋值

  • 分享几种python 变量合并方法

    目录 一.list 合并 二.str 合并 三.dict 合并 一.list 合并 第一种方法: a =[91,95,97,99] b =[92,93,96,98] c = a+b  # 合并 c.sort()  # 排序  正序 print(c) c.sort(reverse=True)  # 排序  倒序 print(c) 第二种方法: a =[91,95,97,99] b =[92,93,96,98] a[0:0] = b # 合并 a.sort() print(a) 第三种方法: a =

  • pgsql 变量赋值方法及注意事项

    1.网上一般说的方法如下: :=,赋值,比如user_id := 20; select into 赋值,比如 SELECT INTO myrec * FROM emp WHERE empname = myname 2.我今天介绍的是一个更通用更实用的赋值方法 select ...into ... 使用示例: 一个变量,select 30 into user_id; 多个变量,select 20,30,50 into a,b.c; 3.在存储函数中(即存储过程中)还有Into也很常用. 比如,拼接

  • go和python变量赋值遇到的一个问题

    平时写得多的是python,最近看了一点go,今天碰到了一个问题,和大家分享一下 package main import "fmt" type student struct { Name string Age int } func pase_student() { m := make(map[string]*student) stus := []student{ {Name: "zhou", Age: 24}, {Name: "li", Age:

  • Python中的变量赋值

    目录 1 变量.对象.引用 2 对象的垃圾回收机制 3 变量所指向的对象不同会有何不同? 引言: Python中的变量在使用中很流畅,可以不关注类型,任意赋值,对于开发来说效率得到了提升,但若不了解其中的机理,往往也会犯一些小错,让开发进行的不那么流畅,本文就是从语言设计和底层原理的角度,带大家理解Python中的变量. 下面我们从一个简单例子开始: a = 3 当我们代码中写入a=3时到底发生了啥,从概念上来说,Python会执行三个不同的步骤来完成这个请求: 创建了一个对象来代表值3 若是a

  • 深入理解Python变量的数据类型和存储

      我们知道,python的变量是有类型的,对于python变量的几种数据类型,我们在写python时是必须要有一定的概念的.知道数据类型就要知道变量数据类型怎么存储,可是为什么python的变量不需要声明数据类型就可以直接赋值?变量如果有数据类型,那变量不是可以为任意数据类型?那真正的数据类型如int在内存存储的字节大小应该为多少?等等诸如一系列的问题让我提起了的兴趣,经过网上不断查找学习后,在此将我所了解到的内容在此做个总结归纳 一.变量的数据类型 1.什么是变量的数据类型   我们先捋一捋

  • Python 变量类型及命名规则介绍

    首字母为英文和下划线,其它部分则可以是英文.数字和下划线(即:_),而变量名称是区分大小写,即变量temp与Temp为不同变量.变量的基本用法如下: 复制代码 代码如下: # 例:使用变量a = 10b = 20print a + b>>> 30   # 输出a加b的值a = 'hello'b = 'python'print a + ' ' + b>>> hello python  # 输出a加b的值 上面几个例子是使用变量进行运算,python的变量可以分为数字.字符

  • python实现同时给多个变量赋值的方法

    本文实例讲述了python实现同时给多个变量赋值的方法.分享给大家供大家参考.具体分析如下: python中可以同时给多个变量赋值,下面列举了三种方法 # Assign values directly a, b = 0, 1 assert a == 0 assert b == 1 # Assign values from a list (r,g,b) = ["Red","Green","Blue"] assert r == "Red&q

随机推荐