在Python中,变量是没有类型的,这和以往看到的大部分编辑语言都不一样。在使用变量的时候,不需要提前声明,只需要给这个变量赋值即可。但是,当用变量的时候,必须要给这个变量赋值;如果只写一个变量,而没有赋值,那么Python认为这个变量没有定义。(在python中,对象赋值实际上是对象的引用。当创建一个对象,然后把它赋给另一个变量的时候,python并没有拷贝这个对象,而只是拷贝了这个对象的引用)

>>> a

Traceback (most recent call last):
File "<pyshell#0>", line 1, in <module>
a
NameError: name 'a' is not defined
>>>

下面我们具体讲一下Python中的变量,引用,拷贝和作用域问题。。

一、可变对象 & 不可变对象

在Python中,对象分为两种:可变对象和不可变对象,不可变对象包括int,float,long,str,tuple等,可变对象包括list,set,dict等。需要注意的是:这里说的不可变指的是值的不可变。对于不可变类型的变量,如果要更改变量,则会创建一个新值,把变量绑定到新值上,而旧值如果没有被引用就等待垃圾回收。另外,不可变的类型可以计算hash值,作为字典的key。可变类型数据对对象操作的时候,不需要再在其他地方申请内存,只需要在此对象后面连续申请(+/-)即可,也就是它的内存地址会保持不变,但区域会变长或者变短。

二、变量无类型,对象有类型

上面说了,Python中的变量是没有类型的,但Python其实是区分类型的:Python的所有变量其实都是指向内存中的对象的一个指针,都是值的引用,而其类型是跟着对象走的。总结来说:在Python中,类型是属于对象的,而不是变量, 变量和对象是分离的,对象是内存中储存数据的实体,变量则是指向对象的指针。在《Learning Python》一书中有一个观点:变量无类型,对象有类型,大概也是说的这个意思。

例如:

对象VS变量

 
nfoo = 1 #一个指向int数据类型的nfoo(再次提醒,nfoo没有类型)
 
lstFoo = [1] #一个指向list类型的lstFoo,这个list中包含一个整数1

下面是一张说明变量的图:

Python函数参数到底是按值还是按引用传递的

def func_int(a):
a += 4 def func_list(a_list):
a_list[0] = 4 t = 0
func_int(t)
print t
# output: 0 t_list = [1, 2, 3]
func_list(t_list)
print t_list
# output: [4, 2, 3]

对于上面的输出,不少Python初学者都比较疑惑:第一个例子看起来像是传值,而第二个例子确实传引用。其实,解释这个问题也非常容易,主要是因为可变对象和不可变对象的原因:对于可变对象,对象的操作不会重建对象,而对于不可变对象,每一次操作就重建新的对象。

在函数参数传递的时候,Python其实就是把参数里传入的变量对应的对象的引用依次赋值给对应的函数内部变量。参照上面的例子来说明更容易理解,func_int中的局部变量"a"其实是全部变量"t"所指向对象的另一个引用,由于整数对象是不可变的,(你想修改不可更改的对象时,其实就是开辟了一个新的存储空间新的对象)所以当func_int对变量"a"进行修改的时候,实际上是将局部变量"a"指向到了整数对象"1"。所以很明显,func_list修改的是一个可变的对象,局部变量"a"和全局变量"t_list"指向的还是同一个对象。

Python中的变量、引用、拷贝和作用域的更多相关文章

  1. Python中的变量引用对象需注意的几点

    Python中的变量引用对象需注意的几点 分类:Python (55)  (0) 普通引用: Python中,变量的作用仅仅是一个标识,只有赋值后才被创建,它可以引用任何类型的对象,而且在引用之前必须 ...

  2. python中的变量引用小结

    python的变量都可以看成是内存中某个对象的引用.(变量指向该内存地址存储的值) 1.python中的可更改对象和不可更改对象 python中的对象可以分为可更改(mutable)对象与不可更改(i ...

  3. Python中的变量和作用域详解

    Python中的变量和作用域详解 python中的作用域分4种情况: L:local,局部作用域,即函数中定义的变量: E:enclosing,嵌套的父级函数的局部作用域,即包含此函数的上级函数的局部 ...

  4. python学习(九)python中的变量、引用和对象的关系

    <Think In Java>中说到过"万事万物皆对象",这句话也可以用在Python中. 感觉Python中的变量有点像Javascript中的变量,是弱类型的,但是 ...

  5. Python 中的变量

    Python采用基于值得内存管理模式,赋值语句的执行过程是:首先把等号右侧标识的表达式计算出来,然后在内存中找一个位置把值存放进去,最后创建变量并指向这个内存地址.Python中的变量并不直接存储值, ...

  6. Python中的变量和常量

    本文主要介绍Python中的变量和常量,包括变量的命名规范,使用注意事项 -------------- 完美的分割线 --------------- 1.变量 1.1.变量理解 1)什么是变量 变量即 ...

  7. python中的变量与对象

    一. 什么是变量 变量就是以前学习的数学中常见的等式x = 3(x是变量,3是变量值),在编程中,变量不仅可以是数学,还可以是任意数据类型 二. 变量的命名规则 变量名必须是英文大小写.数字和_的组合 ...

  8. MyBatis mapper文件中的变量引用方式#{}与${}的差别

    MyBatis mapper文件中的变量引用方式#{}与${}的差别 #{},和 ${}传参的区别如下:使用#传入参数是,sql语句解析是会加上"",当成字符串来解析,这样相比于$ ...

  9. python中的变量和数据类型

    一.变量定义:变量是计算机内存中的一块区域,存储规定范围内的值,值 可以改变,通俗的说变量就是给数据起个名字. 二.变量命名规则: 1. 变量名由字母.数字.下划线组成 2. 数字不能开头 3. 不可 ...

随机推荐

  1. PAT 解题报告 1047. Student List for Course (25)

    1047. Student List for Course (25) Zhejiang University has 40000 students and provides 2500 courses. ...

  2. Swift游戏实战-跑酷熊猫 01 创建工程导入素材

    在这节里,我们将建立一个游戏工程,并导入一些必要的素材,例如序列帧动画文件,声音素材文件.动画文件我们使用atlas形式.在打包发布或者模拟器测试的时候,它会将整个.atlas文件夹下的图片打包成一张 ...

  3. AIR 中的 File 对象 所访问的文件夹位置

    AIR 中的 File 对象 所访问的文件夹位置 Link 关于File.cacheDirectory的一点说明 According to the Apple guidelines, data tha ...

  4. java系统时间的调用和格式转换

    java在java.text   java.util   java.lang包中查找 import java.util.*; import java.text.*; public class Text ...

  5. Java基础(8):方法重载的4个依据与例子

    判断方法重载的依据: 1. 必须是在同一个类中 2. 方法名相同 3. 方法参数的个数.顺序或类型不同 4. 与方法的修饰符或返回值没有关系 运行结果:

  6. UVA 10498 Happiness(线性规划-单纯形)

    Description Prof. Kaykobad has given Nasa the duty of buying some food for the ACM contestents. Nasa ...

  7. Linux(CentOS) 如何查看当前占用CPU或内存最多的K个进程

    一.可以使用以下命令查使用内存最多的K个进程 方法1: ps -aux | sort -k4nr | head -K 如果是10个进程,K=10,如果是最高的三个,K=3 说明:ps -aux中(a指 ...

  8. RobotFramework 安装配置(一)

    服务器接口的测试框架的选择,最后选中了 RobotFramework ,原因一:能有效的管理测试用例,,支持批量执行,能实现关键字驱动或者数据驱动.原因二:支持测试人员可以使用Python和java创 ...

  9. zw版【转发·台湾nvp系列Delphi例程】HALCON EdgesImage

    zw版[转发·台湾nvp系列Delphi例程]HALCON EdgesImage procedure TForm1.Button1Click(Sender: TObject);var img0, im ...

  10. yii2细节设置

    1.设置默认的跳转登陆页面.默认的登陆成功页 在项目的(backend/frontend的config中的main.php中的user组件中),添加loginUrl=>'admin/login' ...