python函数进阶
1. 匿名函数
语法: lambda params(参数列表):expression
- 定义函数 x + y
def fun(x, y):
return x + y
print(fun(1, 3))
输出结果:
4
- 使用匿名函数实现
a = lambda x,y:x+y
print(a(2,3))
输出结果:
5
2. sorted
sorted(iterable, key=None, reverse=False)
- iterable:可迭代对象, 比如列表
- key:自定义排序方式
- reverse=True 表示降序,省略不写则默认为升序
1、 元组中数字大小排序
# 1. 普通函数实现
my_list = [
('a', 5),
('a', 2),
('a', 1),
('a', 6)
]
def f(x):
return x[1]
print(sorted(my_list, key=f, reverse=True))
# [('a', 6), ('a', 5), ('a', 2), ('a', 1)]
# 2. 匿名函数实现
my_list = [
('a', 5),
('a', 2),
('a', 1),
('a', 5),
('a', 6)
]
print(sorted(my_list, key=lambda x: x[1], reverse=True))
# [('a', 6), ('a', 5), ('a', 5), ('a', 2), ('a', 1)]
2、字典年龄大小排序
a = [
{'name': '小白', 'age': 13},
{'name': '小红', 'age': 19},
{'name': '小兰', 'age': 11}
]
z = sorted(a, key=lambda x: x['age'])
print(z)
# [{'name': '小兰', 'age': 11}, {'name': '小白', 'age': 13}, {'name': '小红', 'age': 19}]
3. map
语法:map(函数, 可迭代对象[, 可迭代对象, ...])
它返回的是一个迭代器,原来的列表不变
1、 计算列表中各个元素的平方数
my_list = [1, 2, 3, 4, 5, 6]
# ① 普通方式
res = []
for i in my_list:
res.append(i ** 2)
print(res)
打印结果:
[1, 4, 9, 16, 25, 36]
# ② 普通函数
def f(x):
return x * x
my_list = [1, 2, 3, 4, 5, 6]
res = map(f, my_list)
print(list(res))
打印结果:
[1, 4, 9, 16, 25, 36]
# ③ map映射 匿名函数 map(func, list)
my_list = [1, 2, 3, 4, 5,6]
res = map(lambda x: x ** 2, my_list)
print(my_list)
print(list(res))
打印结果:可以看到原来的列表my_list没有变化
[1, 2, 3, 4, 5, 6]
[1, 4, 9, 16, 25, 36]
返回结果为迭代器
from collections.abc import Iterable
from collections.abc import Iterator
my_list = [1, 2, 3, 4, 5, 6]
res = map(lambda x: x ** 2, my_list)
print(res) # <map object at 0x0000025666D80FA0>
print('res可迭代对象:', isinstance(res, Iterable)) # True
print('res迭代器:', isinstance(res, Iterator)) # True
print(list(res)) # [1, 4, 9, 16, 25, 36]
步骤:
第一次:从my_list中拿第一个数1, 将这个数当作实参传给匿名函数,匿名函数进行返回,计算得[1]
第一次:从my_list中拿第二个数2, 传入给匿名函数中进行处理,计算得[1,4]
…
第五次:从my_list中拿第五个数5, 传入给匿名函数中进行处理,计算得[1, 4, 9, 16, 25]
总结:
① lambda x:x**2 匿名函数
② x:函数的参数,在这里指列表中每一个元素
③ x的2次方 函数的返回值
④ my_list 列表
2、 两个列表相加
map可以从一个或多个列表中映射出一个列表
# 1. 先使用普通函数实现
def f(x, y):
return x, y
my_list1 = [1, 2, 3]
my_list2 = ['a', 'b', 'c']
xx = map(f, my_list1, my_list2)
print(list(xx))
# 2. 匿名函数实现
my_list1 = [1, 2, 3, 4]
my_list2 = [5, 6, 7, 8]
res = map(lambda x, y: x + y, my_list1, my_list2)
print(list(res))
结果:[6, 8, 10, 12]
步骤:
第一次:从my_list1和my_list1 分别取到1和5, 然后当作实参传递给匿名函数,匿名函数计算并返回,并存储到列表
…
第四次:从my_list1和my_list1 分别取到4和12, 然后当作实参传递给匿名函数,匿名函数计算并返回,并存储到列表
4. reduce
- 两个参数
from functools import reduce
# ① 从1加到10
a = 0
for i in range(1, 11):
a += i
print(a)
# ② reduce()
res = reduce(lambda x, y: x + y, range(1, 11))
print(res)
注意: reduce(func,lst),函数必须有两个参数。
问题:为什么有两个参数 ,但range(1,11)只有1个,怎么不会报错?
解释:
1 2 3 4 5 6 7 8 9 10
第一次 先计算前2个数:1,2 计算得:3
第二次 拿3和第3个数相加:3,3 计算得:6
第三次 拿6和第4个数相加:6,4 计算得:10
第四次 拿10和第5个数相加:10,5 计算得:15
第五次 拿15和第6个数相加:15,6 计算得:21
第六次 拿21和第7个数相加:21,7 计算得:28
第七次 拿28和第8个数相加:28,8 计算得:36
第八次 拿36和第9个数相加:36,9 计算得:45
第九次 拿45和第10个数相加:45,10 计算得:55
2、 reduce第三个参数(初始值)
from functools import reduce
my_list = ['初', '始', '值']
res = reduce(lambda x, y: x + y, my_list, '老铁666')
print(res)
结果:老铁666初始值
在字符'老铁666的基础'上, 开始加列表中的内容
5. filter 过滤
过滤掉不符合条件的元素,返回⼀个 filter 对象(也是迭代器)。
list1 = [3, 0, 1, 6, 9, 7, 0]
res = filter(lambda x: x != 0, list1)
print(list(res))
结果:[3, 1, 6, 9, 7]
from collections.abc import Iterable
from collections.abc import Iterator
list1 = [3, 0, 1, 6, 9, 7, 0]
res = filter(lambda x: x != 0, list1)
print(res) # <filter object at 0x0000017B372DFFA0>
print('res可迭代对象:', isinstance(res, Iterable)) # True
print('res迭代器:', isinstance(res, Iterator)) # True
print(list(res))