一、变量的引用
变量和数据分开存储。变量(数据位置)
a = 1
id(a) #显示a的数据位置
b = a #b记录了a的数据,b也保存了a的数据位置
id(b) #与id(a)相同
a = 2 #a数据位置改变
id(a)
id(b) #b的数据位置不变
引用:变量中记录数据的位置
函数调用是“引用”
def test(num):
print("%d %d" % (num, id(num))) #第一个num仍为10
a = 10
id(a)
test(a) #传递的是a的位置,将num也指向10这个数据
用return返回值,需要用变量接收且变量位置与函数内部定义的return值的位置一致。
返回的是数据位置,而非数据本身
def test(a):
result = "hellow"
return result
a = 10
r = test(a) #r的地址与result一致
二、可变和不可变类型
可变类型
内存中的数据不允许被修改。
类似于先前定义的数据和存储单元一直存在
数字、字符串、元组
a = 1
a = 2 #重新分配了一个空间给2,此时a指向2,而1仍存在,只是a不再指向1
不可变类型
地址不变,存储单元内的数据可变
列表、字典
字典是重新加入新的key和元素
d = {"name": "xiaoming"}
d["age"]=18 #加入了新的元素
d[(1,)] = "元组"
d[1]="整数“ #可以用数字、元组做key,但列表、字典不可以
哈希算法 hash()
接收一个不可变类型的数据作为参数,返回一个整数
作用:提取指定数据的特征码 相同内容得到相同结果,不同内容得到不同结果
hash(1) #输出:1
hash("hello") #输出:5130429270924871373 hello的特征码
hash("hello1") #输出与上面不一样
hash((1,)) #输出该元组的特征码
在设置字典的键值对时,会首先对key进行hash已决定如何在内存中保存字典的数据,以方便后续增删改查
键值对的key必须为不变类型数据
三、局部变量和全局变量(类C)
在python中在函数内部不允许直接修改全局变量的引用
局部变量>全局变量。函数内部输出且内部变量名与外部变量名相同时,输出函数内部所给的值,但全局变量值不变。
在函数内部修改全局变量值的方法 global
num = 10
def test():
global num
num = 99 #num值改为99,在函数外部也变为99
全局变量定义位置——调用函数之前且函数外部即可
全局变量定义名称——建议全局变量与局部变量相同时在全局变量前加g或gl_
四、函数参数和返回值的作用243
函数内部需要处理数据时,设置参数
返回值即return
返回值【进阶】
返回多个值:return 元组/数列/字典
若返回结果为元组,可使用多个变量接收返回结果。 变量个数必须与函数返回值个数相同。
gl_temp, gl-wetness = measure() #measure函数返回两个值
【示例】交换两个数字
#方一 引用新的变量
#方二 利用元组!!!!
a, b = (b , a)
#方三 不利用变量
a = a + b
b = a - b
a = a - b
函数参数为什么内部修改外部不变
等号是赋值的意思,所以在函数内部使用等号时新建了一个区域,num指向新的区域
若传递参数是可变类型,则内变外也变
num从始至终没有改变指向对象
P.S.可以认为就是=的问题/有没有赋值语句的问题
【扩展】+=在列表中等价于执行extend函数,所以内部改变、外部也会改变
五、缺省参数
定义函数时,可以给某个参数定义一个默认值,则该参数即为缺省参数
可以在函数内部定义
gl_num.sort(reverse = Ture) #reverse是参数
指定缺省参数值方法
直接在函数内部定义形参时就赋值(此时为默认值,即没有传递数据时,默认为多少,若传递数据了则该形参等于该数据而非默认值)
注意事项
定义位置
带有默认值的参数放在函数末尾
def print_info(name,gender = True,titile) 错误
def print_info(name,title,gender = True) 正确
调用函数时如果有多个缺省参数,需要指定参数名
def print_info(name,title,gender = True)
... ...
print_info("小美",gender = False) #此时可以忽略title传参
六、多值参数
函数需要处理的参数个数不确定时使用
分类
参数名前加一个*可以接收元组,常用*args
参数名前加两个*可以接收字典,常用**kwargs
kwargs可以记忆键值对参数,args有变量含义
2、3、4、5全部算在元组中
此时即可输入字典
元组和字典的拆包【知道即可】
此时我想让gl_nums进入*args,gl_dict进入**kwargs,但是结果却是元组和字典都传递给了*args,所以需要使用拆包
拆包方式:元组前加*,字典前加**
拆包可以使数据改变等更简单
七、函数递归
函数自己调用自己
参数满足一个条件时,不再继续循环