1、 函数
1. 函数的定义:
函数是封装好的可以重复使用的代码段。
作用提高重复使用效率,提高应用模块性。Python中就有很多内建函数,我们可以直接调用,但是,最重要的是你要事先知道函数的名称和参数。详情可以参考官方文档:
https://docs.python.org/3/library/functions.html
比如print(),但我们可以自己定义函数,这就叫自定义函数。
2. 函数相关知识:
python中内置了很多函数,比如求绝对的的函数:abs,这个只有一个参数。
1) 在命令行模式还可以通过help(abs)查看abs的帮助信息。
2) max函数是接收多个函数,然后返回最大的那个。
3) 还可以给函数设置别名,如 m = min:
4) 数据类型转换函数:
python内置的常用函数还包括数据类型转换函数,比如int()函数可以把其他数据类型转换为整数:
>>> int('123')
123
>>> int(12.34)
12
>>> float('12.34')
12.34
>>> str(1.23)
'1.23'
>>> str(100)
'100'
>>> bool(1)
True
>>> bool('')
False
- 如何自定义一个函数:
- 函数代码块由def关键词开头,函名称和圆括号()后接“:”。
- 任何传入的参数和自变量必须放在圆括号之间。
- 第一行最好用于函数说明。
- return [表达式] 表示结束函数,用于返回值给调用方。
语法格式:
def 函数名 (参数列表):
#注释
函数体
5. 构建一个自定义函数
示例一:
注释:此处构建了一个abs求绝对值函数(python中内建了abs函数,而此处应该把名字改为my_abs最为恰当)
6. 形参和实参
此处的x又叫形式参数(形参)。90又叫实际参数(实参)
示例二:
7. 保存定义的函数:
如果你已经把abs()的函数定义保存为abstest.py文件了,那么,可以在该文件的当前目录下启动Python解释器,用from abstest importabs来导入abs()函数,注意abstest是文件名(不含.py扩展名)
8. 函数的调用
定义一个函数:给了函数一个名称,指定了函数里包含的参数,和代码块结构
这个函数的基本结构完成以后,你可以通过另一个函数调用执行,也可以直接从 Python 命令提示符执行。
如下实例调用了 printme() 函数:
# 定义函数
def printme( str ):
"打印任何传入的字符串"
print (str);
return;
# 调用函数
printme("我要调用用户自定义函数!");
printme("再次调用同一函数");
9. 空函数
定义一个暂时什么都不做的空函数,可以使用pass语句。
def nop():
pass
10. 必选参数
必需参数须以正确的顺序传入函数。调用时的数量必须和声明时的一样。
调用printme()函数,你必须传入一个参数,不然会出现语法错误:
def printme( str ):
"打印任何传入的字符串"
print (str);
return;
#调用printme函数
printme();
以上实例输出结果:
Traceback (most recent call last):
File “test.py”, line 10, in
printme();
TypeError: printme() missing 1 required positional argument: ‘str’
函数调用使用位置来来确定函数参数值传入的位置,也可以使用参数名来确定参数的位置。
可以允许函数在调用参数位置是不考虑参数的顺序,可以理解为一一匹配。
示例:
def func(a,b=4,c=8):
print('a is :',a,'and b is: ',b,'and c is :',c)
# # #关键字参数
func(125,c = 24)
func(c = 40,a = 80 )
结果:
11. 默认参数
调用函数时,如果没有传递参数会导致无法正常正常调用,而且当我们经常使用某个值的时候,这时默认参数就可以排上用场了。
例:我们设定字符串默认重复次数为2次。
#默认参数
def repeat_str(s,times= 2):
repeated_strs = s * times
return repeated_strs
print(repeat_str('hello'))
print(repeat_str('hello ',5))
结果:
Python依次将键入实参依次对应形参中然后执行函数体,在本次例子中就是,“hello”字符串对应“s”,“5”对应“times”。虽然times是可以变的但是python也能按照必选参数s找到参数的位置,但是当我们在默认参数后面再定义一个必选参数c时,python无法分辨这个“4”是b的参数还是c的参数,所以直接报错。
# #用默认参数之后的函数也必须定义默认参数
def func(a,b=4,c):
print('a is :',a,'and b is: ',b,'and c is :',c)
func(13,4)
报错:
解决办法:
默认参数后面只能跟默认参数。
12. 可变参数(Varargs参数)
顾名思义,就是传入的参数数量是可变的,我们在形参前面加一个*号,可以接收任意个参数。
例:
但是在调用的时候函数接收到一个list和tuple
def calc(*numbers):
print(numbers)
#参数numbers接收到的是一个tuple
#调用:
calc(1,2,3)
calc([1,2,3])
结果:
(1, 2, 3)
([1, 2, 3],)
结果返回两个一样的tuple:只是第二个tuple将list视为一个元素并在后面加“,”以区分(为什么加逗号见tuple基础单一元素处理办法),
当本来就存在一个list时我们只需要将lsit名字前加一个*同样可以成功,例:
结果:
13. 关键字参数:
可变参数允许利用*符号传入一个参数或者多个参数(也就是传入一个list或者tuple),在调用的时候组成一个tuple。
关键字参数也能实现依次传入多个参数,但调用时是自动组装成dict。
也就是我们不光可以传入实参,还可以传入实参的名字。例如“城市:成都”
我们先传入任意个参数:
#关键之参数
def person (name,age,**other):
print('Name is :',name,'Age is : ',age,'Other:',other)
#传入任意个关键字参数
person('leelian',29,city='chengdu',job='python')
结果:
Name is : leelian Age is : 29 Other: {'job': 'python', 'city': 'chengdu'}
可以看出,“**”输出的是dict;类型。
若本来就存在一个dict,我们直接在传入的时候添加“**”转化即可。
14. 命名关键字参数
对于关键字参数,函数调用者可以不受限制的传入参数,但有时我们想限制传入的关键之参数名字,怎么办。这时就要用来命名关键字参数,格式如下:
# 命名关键之参数
def person(name,age,*,city,job):
print(name,age,city,job)
person('leelian',29,city='chengdu',job='python')
结果:
leelian 29 chengdu python
注意:
- 不能省略“*”,否则将直接变成位置参数。
- 命名关键字参数,必须传入参数名。如:city=’chengdu’
- 参数数量不能多也不能少,除非有默认值。
如果函数定义中已经有了一个可变参数,后面跟着的命名关键字参数就不再需要一个特殊分隔符*了:
def person(name, age, *args, city, job):
print(name, age, args, city, job)
15. 参数组合用法:
在Python中定义函数,可以用必选参数、默认参数、可变参数、关键字参数和命名关键字参数,这5种参数都可以组合使用。但是请注意,参数定义的顺序必须是:必选参数、默认参数、可变参数、命名关键字参数和关键字参数。
还可以利用tuple和dict调用此函数:
def f1(a,b,c = 0,*args,**kw):
print('a = ',a,'b = ',b,'c = ',c,'args =',args,'kw =',kw )
def f2(a,b,c = 0,*,d,**kw):
print('a =',a,'b =',b,'c =',c,'d =',d,'kw =',kw )
args = (1,2,3,4)
kw = {'d':99,'x':'#'}
f1(*args,**kw)
args = (1,2,3)
kw = {'d':99,'x':'#'}
f2(*args, **kw)
结果:
a = 1 b = 2 c = 3 args = (4,) kw = {'x': '#', 'd': 99}
a = 1 b = 2 c = 3 d = 99 kw = {'x': '#'}
所以,对于任意函数,都可以通过类似func(*args, **kw)的形式调用它,无论它的参数是如何定义的
小结:
- 必选参数传入的参数数量必须跟声明时一样。
- 默认参数一定要是不可变参数,不能是list,默认参数后不能再跟必选参数。
- 关键字参数:“**”+参数名,如**kw,kw接收的是dict
- 可变参数传入方法一:func(1,2,3)
- 方法二先组装好list或tuple,然后func(*(1,2,3))
17. 参数检查
作用:python解释器只能检查出参数的个数是否正确,而参数类型的错误则无法检查。
个数错误:
类型错误:
所以我们需要利用数据类型检查函数进行数据类型检查:isinstance()
# -*- coding: utf-8 -*-
def my_abs(x):
if not isinstance(x,(int,float)):
raise TypeError('输入的数据不是整形和浮点型')
if x >= 0:
return x
else:
return -x
print (my_abs('aa'))
8. Python函数可以一次返回多个值,因为返回的是一个tuple**
设计一个计算一元二次方程的函数:
# -*- coding: utf-8 -*-
import math
def quadratic(a, b, c):
if not isinstance(a,(int,float)):
raise TypeError('Bad operand type')
if not isinstance(b,(int,float)):
raise TypeError('Bad operand type')
if not isinstance(c,(int,float)):
raise TypeError('Bad operand type')
d = b*b-4*a*c
if d < 0:
print('此方程无解')
elif d == 0:
print('方程只有一个根')
x=b/(2*a)
return x
else :
x1=(-b+math.sqrt(d))/(2*a)
x2=(-b-math.sqrt(d))/(2*a)
print('方程两个解为')
return x1,x2
print (quadratic(1,2,1))
·