您的位置:首页 > 编程语言 > Python开发

Python学习笔记07_函数式编程

2017-02-07 09:10 435 查看

高阶函数Higher-order function

变量可以指向函数,即:函数本身也可以赋值给变量。

函数名也是变量。

把函数作为参数传入,这样的函数称为高阶函数。

map/reduce

map()函数,接收两个参数,一个是函数,一个是Iterable,map将传入的函数依次作用到序列的每个元素,并把结果作为新的Iterator返回。

<<< def f(x):
return x * x

<<< r = map(f, [1, 2, 3, 4, 5, 6, 7, 8, 9])
<<< list(r)
[1, 4, 9, 16, 25, 36, 49, 64, 81]

# map()传入的第一个参数是f,即函数对象本身。

# 由于结果r是一个Iterator,Iterator是惰性序列,

# 因此通过list()函数把整个序列计算出来并返回一个list.


reduce()函数。

reduce(f, [x1, x2, x3, x4]) = f(f(f(x1, x2), x3), x4) # f是两个参数
reduce(f, [x1, x2, x3, x4]) = f(f(f(f(x1), x2), x3), x4) # f是一个参数


# str转换为int的函数

from functools import reduce
def str2int(s):
def fn(x, y):
return x * 10 + y
def char2num(s):
return {'0':0, '1':1, '2':2, '3',3, '4':4, '5':5, '6':6, '7':7, '8':8, '9':9}[s]
return reduce(fn, map(char2num, s))


# str2float

CHAR_TO_FLOAT = {
'0': 0,
'1': 1,
'2': 2,
'3': 3,
'4': 4,
'5': 5,
'6': 6,
'7': 7,
'8': 8,
'9': 9,
'.': -1
}
def str2float(s):
nums = map(lamba ch: CHAR_TO_FLOAT[ch], s)
point = 0
def to_float(f, n):
nonlocal point
if n == -1:
point = 1
return f
if point == 0:
return f * 10 + n
else:
point = point * 10
return f + n /point
return reduce(to_float, num, 0.0)


filter

filter()把传入的函数依次作用于每个元素,然后根据返回值是True还是False决定保留还是丢弃该元素。

filter()函数返回的是一个Iterator,需要用list()函数获得所有结果并返回list。

# 在一个list中,删掉偶数,只保留奇数

def is_odd(n):
return n % 2 == 1

list(filter(is_odd,[1, 2, 3, 4, 5, 6, 9]))


# 把一个序列中的空字符串删掉

def not_empty(s):
return s and s.strip()

list(filter(not_empty, ['A', '', 'B', None, 'C', '  ']))


#!/usr/bin/env python3

# -*- coding: utf-8 -*-

# 用filter求素数

def main():
for n in primes():
if n < 1000:
print(n)
else:
break

# 构造从3开始的奇数序列,注意这是一个生成器,并且是无限序列。

def _odd_iter():
n = 1
while True:
n = n + 2
yield n

# 定义筛选函数

def _not_divisible(n):
return lambda x: x % n > 0

# 定义生成器,不断返回下一个素数

def primes():
yield 2
it = _odd_iter() # 初始序列
while True:
n = next(it) # 返回序列的下一个数
yield n
it = filter(_not_divisible(n), it) # 构造新序列

if __name__ == '__main__':
main()


sorted

对字符串排序,忽略大小写,按照字母序排序,给sorted传入key函数。

sorted(['bob', 'about', 'Zoo', 'Credit'], key = str.lower)


进行反向排序,可以传入第三个参数reverse=True

from operator import itemgetter
students = [('Bob', 75), ('Adam', 92), ('Bart', 66), ('Lisa', 88)]

print(sorted(students, key = itemgetter(0)))
print(sorted(students key = lambda t: t[1]))
print(sorted(students, key = itemgetter(1), reverse = True))


返回函数

函数作为返回值

def lazy_sum(*args):

def sum():

ax = 0

for n in args:

ax = ax + n

return ax

return sum


<<< f1 = lazy_sum(1, 3, 5, 7, 9)

<<< f2 = lazy_sum(1, 3, 5, 7, 9)

<<< f1 == f2

False


闭包,返回的函数并没有立即执行,返回函数不要引用循环变量,或者后续会发生变化的变量。

匿名函数

匿名函数只能有一个表达式,不用写return,返回值就是该表达式的结果。匿名函数也是一个函数对象,可以把匿名函数赋值给一个变量,再利用变量来调用该函数。

<<< list(map(lambda x: x * x), [1, 2, 3, 4, 5, 6, 7, 8, 9])

# 关键字lambda表示匿名函数,冒号前面的x表示函数参数。


装饰器

装饰器,在代码运行期间动态增加功能。

import functools

def log(func):
@functools.wraps(func)
def wrapper(*args, **kw):
print('call %s():' % func.__name__)
return func(*args, **kw)
return wrapper

@log
def now():
print('2015-3-25')

<<< now()

# now = log(now)

call now():
2015-3-25


import functools

def log(text):
def decorator(func):
@functools.wrap(func)
def wropper(*args, **kw):
print('%s %s' % (text, func.__name__))
return func(*args, **kw)
return wrapper
return decorator

@log('execute')
def now():
print('2015-3-25')

<<< now()

# now = log('execute')(now)

execute now():
2015-3-25

<<< now.__name__
'wrapper'


偏函数Partial function

functools.partial,创建偏函数时,实际上可以接收函数对象、
*args
**kw
这三个参数.

def int2(x, base = 2):
return int(x, base)


<<< import functools
<<< int2 = functools.partial(int, base = 2)
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: