Python之Map,Reduce和 Filter

一、Map

1.1 定义及基础用法

Map会将一个函数映射到一个输入序列的所有元素上。Map() 会根据提供的函数对指定序列做映射。

第一个参数 function 以参数序列中的每一个元素调用 function 函数,返回包含每次 function 函数返回值的新列表。

func是None的情况,它的目的是将多个列表相同位置的元素归并到一个元组,在现在已经有了专用的函数zip()了。

不同长度的多个seq是无法执行map函数的,会出现类型错误。

基础语法:

map(function_to_apply, list_of_inputs)
map(*function*, *iterable*, *...*) -> list
参数:

function_to_apply:映射函数,也就是处理输入迭代类型的的每一个元素的函数。

list_of_inputs:一个或多个序列。输入的序列类型:列表,集合,元组,字典及字符串。

返回值: 

    Python2 :map直接返回列表,不管输入的迭代类型是列表,集合,元组,字典还是字符串类型。

    Python3:map返回迭代器,可以利用list()转为列表,只能转为列表,set(), tuple()等函数不起作用。

Iterator是惰性序列,因此通过list函数让它把整个序列都计算出来并返回一个list。

示例:

Python 2:

a = [1, 2, 3, 4]
b = map(lambda x: x*2, a)   # 处理列表
Out[4]: [2, 4, 6, 8]
 
b = map(lambda x: x*2, (1,2,3))  # 处理元组
Out[6]: [2, 4, 6]
 
b = map(lambda x: x*2, {1:2, 3:4, 5:6})  # 处理字典,只处理键
Out[8]: [2, 6, 10]
b = map(lambda x: x*2, {1:2, 3:4, 5:6}.keys())
Out[17]: [2, 6, 10]
 
b = map(lambda x: x*2, {1:2, 3:4, 5:6}.values())
Out[15]: [4, 8, 12]
 
b = map(lambda x: x*2, set([1, 2, 3, 4]))  # 处理集合
Out[11]: [2, 4, 6, 8]
 
b = map(lambda x: x+"1", "12345") # 处理字符串,字符串也是迭代类型
Out[19]: ['11', '21', '31', '41', '51']
Python 3

>>> a = [1, 2, 3, 4]
>>> b = map(lambda x: x*2, a)   # 处理列表
>>> b
<map object at 0x0000000002B68A20>   # map对象
>>> list(b)
[2, 4, 6, 8]
1.2 高级用法

1.2.1 处理多个序列

想要输入和处理多个序列,需要可以支持多个参数的函数,注意的是各序列的长度必须一样,否则报错。
# 提供了两个列表,对相同位置的列表数据进行相加
>>> map(lambda x, y: x + y, [1, 3, 5, 7, 9], [2, 4, 6, 8, 10])
[3, 7, 11, 15, 19]
>>> map(add,'zhoujy','Python','test')     #'test'的长度比其他2个小
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: add() takes exactly 2 arguments (3 given)
 

单个序列:seq中的每个元素都经过了func函数的作用,得到了func(seq[n])组成的列表。

 

多个序列:每个seq的同一位置的元素在执行过一个多元的func函数之后,得到一个返回值,这些返回值放在一个结果列表中。

print map( lambda x, y: x * y, [1, 2, 3], [4, 5, 6] )  # [4, 10, 18]
print map( lambda x, y: ( x * y, x + y), [1, 2, 3], [4, 5, 6] )  # [(4, 5), (10, 7), (18, 9)]
 返回值是一个值,也可以是一个元组。

1.2.2 处理函数序列

大多数时候,我们使用匿名函数(lambdas)来配合map,  不仅可以用于一序列的输入, 也可以用于一列表的函数。

def multiply(x):
        return (x*x)
def add(x):
        return (x+x)
 
funcs = [multiply, add]
for i in range(5):
    value = map(lambda x: x(i), funcs)
    print(list(value))
    # 译者注:上面print时,加了list转换,是为了python2/3的兼容性
    #        在python2中map直接返回列表,但在python3中返回迭代器
    #        因此为了兼容python3, 需要list转换一下
 
# Output:
# [0, 0]
# [1, 2]
# [4, 4]
# [9, 6]
# [16, 8]
二、Reduce

2.1 定义及基础用法

       reduce() 函数会对参数序列中元素进行累积。

函数将一个数据集合(列表,元组等)中的所有数据进行下列操作:用传给 reduce 中的函数 function(有两个参数)先对集合中的第 1、2 个元素进行操作,得到的结果再与第三个数据用 function 函数运算,最后得到一个结果,逐步迭代。

   也就是reduce函数把前两个元素的计算结果继续和序列的下一个元素做累积计算,直到处理完所有元素,返回结果。以下两个函数等价:

reduce(f, [x1, x2, x3, x4]) = f(f(f(x1, x2), x3), x4)
基本语法:

reduce(function, iterable[, initializer])
reduce(*function*, *iterable*[, *initializer*]) -> value
参数:

function -- 函数,有两个参数
iterable -- 可迭代对象
initializer -- 可选,初始参数。第一次时为init的元素,如没有init则为seq的第一个元素。
返回值:

返回函数计算结果。

示例:

>>>def add(x, y) :            # 两数相加
...     return x + y
... 
>>> reduce(add, [1,2,3,4,5])   # 计算列表和:1+2+3+4+5
15
>>> reduce(lambda x, y: x+y, [1,2,3,4,5])  # 使用 lambda 匿名函数
15
上述执行过程是:1+2=3,3+3=6,6+4=10,10+5=15。

2.2 高级用法

2.2.1 处理函数序列

使用匿名函数(lambdas)来配合reduce,  不仅可以用于一序列的输入, 也可以用于一个函数序列,但是要注意lambda表达式的参数是两个。

def multiply(x):
    return (x * x)
 
 
def add(x):
    return (x + x)
 
 
funcs = [multiply, add]
    for i in range(5):
        value = reduce(lambda x, y: x(i) + y(i), funcs)
        print(value)
 
0
3
8
15
24
三、Filter

3.1 定义及基础用法    

Python 2:      

 filter() 函数用于过滤序列,过滤掉不符合条件的元素,返回由符合条件元素组成的新列表。

Python 3:

filter() 函数用于过滤序列,过滤掉不符合条件的元素,返回一个迭代器对象,如果要转换为列表,可以使用 list() 来转换,利用set转换为集合,tuple转换为元组,str转为字符串。

另外注:集合是{},列表是[],元组是(),字典是{k1:v1, k2:v2}。

       注意: Pyhton2.7 返回列表,Python3.x 返回迭代器对象。

       Filter是一个内置函数,并且比for循环更快。

基本语法:

filter(function, iterable)
filter(function or None, sequence) -> list, tuple, or string
参数:

       其接收两个参数,第一个为函数,第二个为序列,序列的每个元素作为参数传递给函数进行判断,然后返回 True 或 False,最后将返回 True 的元素放到新列表中。

function -- 判断函数。过滤序列中每个元素的函数。
iterable -- 可迭代对象。需要过滤的序列。
返回值:

       Python 2:返回序列,不只是列表,也可能是元组,字符串。

       列表,集合,字典返回列表,元组返回元组,字符串返回字符串。字典处理键。

       Python 3:返回一个迭代器对象,filter object(filter对象)。

Python3 中返回到是一个 filter 类对象。filter 类实现了 __iter__ 和 __next__ 方法, 可以看成是一个迭代器, 有惰性运算的特性(类似于生成器), 相对 Python2.x 提升了性能, 可以节约内存。

a = filter(lambda x: x % 2 == 0, range(10))
print(a)
输出:

<filter object at 0x0000022EC66BB128>
示例:

Python 2:

过滤出列表中的所有奇数:

def is_odd(n):
    return n % 2 == 1
 
newlist = filter(is_odd, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
print(newlist)
 
[1, 3, 5, 7, 9]
Python 3:

def is_odd(n):
    return n % 2 == 1
 
tmplist = filter(is_odd, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
newlist = list(tmplist)
print(newlist)
 
[1, 3, 5, 7, 9]
四、总结:

(1)map函数和map函数与MapReduce的机制原理相同。map函数对序列的每一个元素进行处理,而resuce函数则两两迭代逐步计算。

(2)reduce函数和filter函数只能处理一个序列。

(3)注意在 python2 和 python3 中,map/reduce/filter 的返回值类型有所不同,python2 返回的是基本数据类型,而 python3 则返回了迭代器。

(4)filter函数很容易被for循环和for in if推导式所替代。
————————————————
原文链接:https://blog.csdn.net/answer3lin/article/details/86505932

其他参考:https://www.jianshu.com/p/107d2eb45558

https://blog.csdn.net/weixin_44554475/article/details/90696711

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值