函数
先看函数的形式
def hello() :
print("Hello World!")
#格式如下
def 函数名(参数列表):
函数体
return
#函数体是必须缩进,函数列表后必须跟 :
def hello(name):
print('hello %s' %(name))
hello('python')
#输出
hello python
默认参数值,对一个或多个参数指定一个默认值。这样创建的函数,可以用比定义时允许的更少的参数调用,比如:
def hello(name, time='2020'):
return ('hello %s, %s' %(name, time))
print(hello('python'))
#输出
hello python, 2020
默认值是在定义过程中在函数定义处计算的,比如:
time = '2021'
def hello(name, time=time):
return ('hello %s, %s' %(name, time))
print(hello('python'))
time = 2022
print(hello('python'))
#输出
hello python, 2021
hello python, 2021
#要输出不一样的结果
time = 2022
print(hello('python', time=time)
#输出
hello python, 2022
仔细看了下python的学习文档,发现函数还有一些细节,比如关键字参数,特殊参数,位置参数等细节。以前学习的时候并没有注意到。
关键字参数是形如 kwarg=value 的关键字参数来调用函数。例如下面的函数:
def hello(name, time='2020', ask='how are you'):
return ('hello %s, %s' %(name, time))
接受1个必需的参数(name)和2个可选的参数(time和ask),可以如下面调用
hello('python')
hello(name='python')
hello(name='python', time='2021', ask='')
hello(time='2021',name='python')
name参数是必须要给出的,否则报错。
因为赋给形参的值是根据位置而赋值的,因此形参列表中带有默认参数的参数要放在最后。
如,def fun(a, b=0) 是正确,但是 def fun(a=2, b) 错误。
python参数传递
- 不可变类型:类似 C++ 的值传递,如 整数、字符串、元组。如 fun(a),传递的只是 a 的值,没有影响 a 对象本身。如果在 fun(a))内部修改 a 的值,则是新生成来一个 a。
def change(a):
print(id(a)) # 指向的是同一个对象
a=10
print(id(a)) # 一个新对象
a=1
print(id(a))
change(a)
输出
8791291385504
8791291385504
8791291385792
函数内的a=10,实际是新的一个对象和函数外的a=1是不一样的。
- 可变类型:类似 C++ 的引用传递,如 列表,字典。如 fun(la),则是将 la 真正的传过去,修改后 fun 外部的 la 也会受影响
def fun(a, b=[]):
print(b)
return b
res = fun(1, [3])
print(res)
res.append(56)
fun(2)
print(res)
输出
[3]
[3]
[]
[3, 56]
在传递可变类型的参数需要小心谨慎。那如果需要传递一个列表,字典等,该如何做?
不定长参数
Python 提供了一种元组的方式来接受没有直接定义的参数。这种方式在参数前边加星号 *
。像不像C/C++中的指针参数?
def my_function(a, b= 3, *kids):
print("The youngest child is " + kids[2])
print(type(kids))
print(kids, b)
my_function(1, '4', "Phoebe", "Jennifer", "Rory", [1,2])
输出
The youngest child is Rory
<class 'tuple'>
('Phoebe', 'Jennifer', 'Rory', [1, 2]) 4
这里可看出,参数是按照位置对应的,另外kid是个元组,那如果是带两个**的参数会是什么情况?
def my_function(a, b= 3, **kids):
print("The youngest child is {} ".format(kids['kids'][1]))
print(type(kids))
my_function(1, '4', kids = ("Phoebe", "Jennifer", "Rory", [1,2]))
输出
The youngest child is Jennifer
<class 'dict'>
**kids
是关键字参数,是字典类型。
只接受关键字参数
如果希望函数的参数必须强制使用关键字参数,怎么办?这种情况比如上面案例中,b=3,如果不强制传参数的时候指定b=3的形式,那么就会按照参数的位置传值,被赋值'4'。
这时候就需要用应该 * 将强制关键字参数放到某个*
参数或者单个*
后面就能达到这种效果,比如:
def my_function(a, *, b= 3, **kids):
print("The youngest child is {} ".format(kids['kids'][1]))
print(type(kids))
my_function(1, '4', kids = ("Phoebe", "Jennifer", "Rory", [1,2]))
这种的传参会输出报错:
Traceback (most recent call last):
File "hello.py", line 118, in <module>
my_function(1, '4', kids = ("Phoebe", "Jennifer", "Rory", [1,2]))
TypeError: my_function() takes 1 positional argument but 2 were given
#这样则不会报错
my_function(1, b='4', kids = ("Phoebe", "Jennifer", "Rory", [1,2]))
输出
The youngest child is Jennifer
<class 'dict'>
4
使用强制关键字参数会必达更清晰,程序可读性高。使用强制关键字参数也会比使用 **kw
参数更好且强制关键字参数在一些更高级场合同样也很有用。
接下来将要复习:模块