3.16学习笔记
复习
#1.参数
#2.返回值
是否产生新的数据
#3.全局变量和局部变量
全局变量:是否没有定义在函数或类内
局部变量:是否定义在函数内
#4.匿名函数
变量 = lambda 参数列表:返回值
新的知识点
一、函数就是变量
1.函数的本质
python中定义函数其实就是在定义一个类型是function的变量;函数名就是变量名。
变量能做的函数都能做
a = 10
b = ‘abc’
c = [1,29,8]
d = {‘a’:23,‘b’:100}
e = lambda x: x*2
def e(x):
return x*2
def func1(): #func1是变量
print(‘函数’)
2.变量的常用操作
#1)
x1 = a
print(x1,x1+ 10)
x2 = func1
x2()
#2)
list1 = [a,100]
print(list1,list1[0] * 10)
list1 = [func1,100]
print(list1,`list1[0]()`)
#3)
a=100
print(a)
func1 = 100
print(func1)
#4)
def func2(x)
print(x)
def func1(): #func1是变量
print('函数')
a=10
func2(a)
func2(func1)
#5)
def func3()
aa=10 #返回值高阶函数
return aa
def func4():
def fn()
print('小函数')
return fn
func4()() #fn()
二、高阶函数
实参高阶函数:如果一个函数的参数是函数,那么这个函数就是实参高阶函数。(掌握怎么使用系统提供的实参高阶函数)
返回值高阶函数:如果一个函数的返回值是函数,那么这个函数就是返回值高阶函数。(会写装饰器)
def test(x):
x() #必须是不需要参数的函数
1.常用实参高阶函数:max、min、sorted、map、reduce
1)max和min
max(序列,key = 函数)
sorted(序列,key = 函数)
函数要求:
a.有且只有一个参数,这个参数指向的数前面序列中的每个元素
b.需要一个返回值,返回值决定求最大值的时候比较的对象
nums = [29,87,65,9,25]
print(max(nums)) #基本用法
#求列表nums中个位数最大的元素 :19
nums = [28,87,65,19,25]
result = max(nums,key = lambda item:item % 10) #19
print(result)
#求列表nums中十位数最大的元素 : 85
nums = [28,607,65,19,85]
result = max(nums,key = lambda item:item // 10 % 10)
print(result)
#求列表nums中绝对值最大的元素 :-650
nums = [28,607,-650,19,-85]
result = max(nums,key = lambda item:item**2)
或
result = max(nums,key = lambda item:item if item>0 else -item)
print(result)
练习:求列表中各个位上和最大的元素
nums = [28,607,65,19,88]
result = max(nums,key = lambda item:sum([int(x) for x in str(item)]))
print(result)
#用min获取students中年龄最小的学生
students =[
{'name','小明',‘age':18,'score':98,'tel':'187283822'},
{'name','小红',‘age':30,'score':99,'tel':'187283827'}
{'name','Tom',‘age':25,'score':87,'tel':'187283828'}
{'name','Bob',‘age':19,'score':65,'tel':'187283829'}
]
result = min(students,key=lambda stu: stu['age'])
print(result)
或
result=reduce(lambda x,item: x+item['score'],nums,0)/len(students)
将列表中的元素按个位数从小到大排序
nums = [28,87,65,19,25]
result = sorted(nums,key = lambda item:item % 10)
print(result) #[65,25,87,28,19]
students.sort(key=lambda stu: stu['tel'][-1])
print(students)
#求nums数字数值最大的元素
nums=[23,'38','2893',89]
result = max(nums,key=lambda item:int(item))
print(result)
2)map函数:将原序列中元素按照指定的标志进行变换
#map(函数,序列)
函数的要求:
a.有且只有一个参数,这个参数指向的是后面这个序列每个元素
b.需要返回值,描述新序列中的元素和原序列中元素的关系
#[28,89,34,78,21] -> [8,9,4,8,1]
nums = [28,89,34,78,21]
result = map(lambda item: item % 10,nums)
print(list(result)) #[8,9,4,8,1]
#map(函数,序列1,序列2)
函数要求:
a.有且只有两个参数,这两个参数分别指向后面的两个序列中的元素
b.需要返回值,描述新序列中的元素和原序列中元素的关系
nums1 = [10,20,30,40]
nums2 = [100,200,300,400]
result = map(lambda item1,item2: item1+item2,nums1,nums2)
print(list(result)) #[110,220,330,440]
练习:
scores = [28,89,67,56,34,90]
ages = [23,30,19,24,25,23]
#[{'score':29,'age':23},{'score':89,'age':30},...]
result = map(lambda item1,item2: {'score':item1,'age':item2},scores,ages)
print(list(result))
values = ['小明',18,90]
keys = ['name','age','score']
{'name','age':18,'score':90}
result = map(lambda item1,item2: (item1,item2),keys,values)
print(list(result))
#map(函数,序列1,序列2,序列3)
- reduce
from functools import reduce
#reduce函数—将序列中所有的元素通过指定的方式合并成一个数据
reduce(函数,序列,初始值)
函数的要求:
a.有且只有两个参数:第一个第一次指向初始值,从第二次开始指向上一次的计算结果;第二个参数指向序列中的每个元素
b.需要返回值,返回值用来描述合并规则
nums = [20,34,45,10]
result = reduce(lambda x,item: x+item,nums,0)
print(result)
reduce内部执行过程:
循环5次:
第1次
x=0, item=20, x=x+item=0+20=20
第2次
x=20, item=34, x=x+item=20+34=54
第3次
x=54, item=45, x=x+item=54+45=99
第4次
x=99, item=10, x=x+item=99+10=109
return x
nums=[2,4,5,6,3]
#2*4*5*6*3
result = reduce(lambda x,item: x*item,nums,1)
print(result)
#'24563'
result = reduce(lambda x,item: x+str(item),nums,'')
print(result)
#203040506030
result = reduce(lambda x,item: f'{x}{item}0',nums,'')
print(result)
nums=[23,'45',10,2,'30']
#23+45+10+2+30
result = reduce(lambda x,item: x+int(item),nums,0)
print(result)
#23+10+2
result = reduce(lambda x,item: x+item(if type(item)==int else 0),nums,0)
print(result)
三、装饰器
1.什么是装饰器
装饰器=实参高阶函数+返回值高阶函数+糖语法
装饰器是用来给函数添加功能的
2.给函数添加本功能
方法一:在需要添加功能的函数中添加代码
问题:如果要给不同的函数添加相同的功能,相同的代码会重复写
from time import time
def func1():
start=time()
print('hello world!')
end=time()
print('执行时间:',end - start)
def func2(N: int):
start=time()
result = reduce(lambda x,item: x*item,range(1,N+1),1)
print(result)
end = time()
print('执行时间:',end - start)
方法二:将需要添加的功能封装成函数
调用函数时需要调用的时候新增功能,而不是添加过功能的原函数
def count_time(fn, *args, **kwargs):
#fn = func22
start = time()
fn(*args, **kwargs) # 执行函数
func22()
end = time()
print('执行时间:', end - start)
def func11():
print('hello world!')
def func22(N: int):
result = reduce(lambda x, item: x * item, range(1, N + 1), 1)
print(result)
def func33(a, b, c):
print(f'a:{a}, b:{b}, c:{c}')
count_time(func11)count_time(func22, 4)
#func33(10, 20, 30)count_time(func33, 10, 20, c=30)
#补充*的用法:打包、解包
def f1(*nums):
print(nums)
f1(2, 3, 4)
# nums = (2, 3, 4)
x, *y = 10, 20, 30, 40
t = (1, 11, 22)
print(t)
# (1, 11, 22)
print(*t)
print(1, 11, 22) -> 1 11 22
d = {'a': 10, 'b': 20} # **d -> a=10, b=20
d2 = {'end': ';', 'sep': ','}
print('abc', 123, **d2)
# print('abc', 123, end=';', sep=',')
def f2(f, *n, **kwargs):
# f = f3, n = (10, 20, 30)
f(*n, **kwargs)
# f3(10, 20, 30)
f3(x=10, y=20, z=30)
def f3(x, y, z):
print('函数')f2(f3, x=10, y=20, z=30)
方法三:装饰器
def 装饰器名称(需要添加功能的函数):
def 添加过功能的新函数(*args,**kwargs):
需要添加功能的函数(*args,**kwargs)
添加新的功能
return 添加过功能的新函数
def count_time(f):
new_f(*args,**kwargs):
start =time()
f(*args,**kwargs)
end = time()
print(f’执行时间:{end - start}’)
# 练习1:写一个装饰器,给函数添加功能,然后原函数结束的时候打印一个’end’
def add_end(f):
def new_f(*args, **kwargs):
result = f(*args, **kwargs)
print('end')
return result
return new_f
@add_end
def func2():
print('hello world!')
func2()
# 练习2:写一个装饰器,将函数的返回值加100。 1 -> 101
def value_add(f):
def new_f(*args, **kwargs):
result = f(*args, **kwargs)
if type(result) in (int, float, bool, complex):
return result + 100
return result
return new_f
@value_add
def func33(N: int):
result = reduce(lambda x, item: x * item, range(1, N + 1), 1)
return result
print(func33(4))
@value_add
def func2():
print('hello world!')
print(func2())