<SYSTEM_TASK:>
Given the following text description, write Python code to implement the functionality described below step by step
<END_TASK>
<USER_TASK:>
Description:
 Lesson 16
v1.1, 2020.5, 2020.6 edit by David Yi
本次内容
闭包：将函数作为值返回
偏函数
高阶函数 map/reduce/filte
Step1:  闭包
在这个例子中，我们在函数 lazy_sum 中又定义了函数 sum，并且，内部函数 sum 可以引用外部函数 lazy_sum 的参数和局部变量，当 lazy_sum 返回函数 sum 时，相关参数和变量都保存在返回的函数中，这种称为“闭包（Closure）”。
一个函数可以返回一个计算结果，也可以返回一个函数。
返回一个函数时，该函数并未执行，返回函数中不要引用任何可能会变化的变量。
闭包和函数的作用域等有关，掌握和理解闭包，对于后续 Python 的深入开发有很大好处，特别是装饰器。
偏函数
python 的 functools 模块提供了很多有用的功能，其中一个就是偏函数（Partial function）。要注意，这里的偏函数和数学意义上的偏函数不一样。
在介绍函数参数的时候，我们讲到，通过设定参数的默认值，可以降低函数调用的难度。而偏函数也可以做到这一点。
Step2:  虽然默认参数还是很容易使用，但是如果我们在某个场景需要大量调用的话，还是有点不方便，特别是对于有很多参数的函数来说，会让程序显得复杂。还记得之前那个 max min 的程序举例么？我们可以用偏函数来解决整个问题。
通过 functools.partial 来进行操作。
Step3:  map() 函数
python内建了 map() 和 reduce() 这两个功能强大的函数。
我们先看 map。map() 函数接收两个参数，一个是函数，一个是可迭代的序列，比如 list，map 将传入的函数依次作用到序列的每个元素，并把结果作为新的 Iterator 可迭代值返回。
举例说明，比如我们有一个函数 f(x) = x*x，要把这个函数作用在一个list [1, 2, 3, 4, 5, 6, 7, 8, 9]上，就可以用map()实现如下：
如果你知道 Google的那篇大名鼎鼎的论文“MapReduce
Step4:  reduce() 函数
再看 reduce 的用法。reduce 把一个函数作用在一个序列[x1, x2, x3, ...]上，这个函数必须接收两个参数，reduce 把结果继续和序列的下一个元素做累积计算，其效果就是：
reduce(f, [x1, x2, x3, x4]) = f(f(f(x1, x2), x3), x4)
Step5:  filter() 函数
Python内建的filter()函数用于过滤序列。
和map()类似，filter()也接收一个函数和一个序列。和map()不同的是，filter()把传入的函数依次作用于每个元素，然后根据返回值是True还是False决定保留还是丢弃该元素。
<ASSISTANT_TASK:>
Python Code:
# 将函数作为值返回
def lazy_sum(*args):
    
    def sum():
        ax = 0
        for n in args:
            ax = ax + n
        return ax
    
    return sum
f = lazy_sum(1, 3, 5, 7, 9)
print(f())
Explanation: Lesson 16
v1.1, 2020.5, 2020.6 edit by David Yi
本次内容
闭包：将函数作为值返回
偏函数
高阶函数 map/reduce/filte
End of explanation
# 进制转换函数
print(int(12345))
print(int('1000',base=2))
print(int('1A',base=16))
Explanation: 闭包
在这个例子中，我们在函数 lazy_sum 中又定义了函数 sum，并且，内部函数 sum 可以引用外部函数 lazy_sum 的参数和局部变量，当 lazy_sum 返回函数 sum 时，相关参数和变量都保存在返回的函数中，这种称为“闭包（Closure）”。
一个函数可以返回一个计算结果，也可以返回一个函数。
返回一个函数时，该函数并未执行，返回函数中不要引用任何可能会变化的变量。
闭包和函数的作用域等有关，掌握和理解闭包，对于后续 Python 的深入开发有很大好处，特别是装饰器。
偏函数
python 的 functools 模块提供了很多有用的功能，其中一个就是偏函数（Partial function）。要注意，这里的偏函数和数学意义上的偏函数不一样。
在介绍函数参数的时候，我们讲到，通过设定参数的默认值，可以降低函数调用的难度。而偏函数也可以做到这一点。
End of explanation
import functools
int2 = functools.partial(int, base=2)
print(int2('1000000'))
print(int2('1010101'))
# 偏函数举例
# 原来的一个函数
def func(x=2,y=3,z=4):
    return x+y+z
print(func(x=3))
print(func(y=6))
print(func(x=4,y=10))
print(func(2,3))
# 构造偏函数，设置默认值
import functools
f1 = functools.partial(func, x=2,z=3)
print(f1(y=3))
print(f1(y=2))
print(f1(2)) # 会报错，不需要再输入 z 的值
Explanation: 虽然默认参数还是很容易使用，但是如果我们在某个场景需要大量调用的话，还是有点不方便，特别是对于有很多参数的函数来说，会让程序显得复杂。还记得之前那个 max min 的程序举例么？我们可以用偏函数来解决整个问题。
通过 functools.partial 来进行操作。
End of explanation
# map 函数举例
def f(x):
    return x * x
r = map(f, [1, 2, 3, 4, 5, 6, 7, 8, 9])
for i in r:
    print(i)
# 这个 f(x) 函数可以比较复杂，包含更多逻辑
def f(x):
    y = x * x + 3
    return y
r = map(f, [1, 2, 3, 4, 5, 6, 7, 8, 9])
for i in r:
    print(i)
# 进行 map 处理的数据也可以复杂一些
def f(x):
    y = x * x + 3
    return y
list1 = [x for x in range(1,100,7) if x % 2 ==0]
print(list1)
# 主要的程序还是很简洁就可以了
r = map(f, list1)
for i in r:
    print(i)
# map 函数也可以同时作用在两组数据上
def addition(x, y):
    return x + y
 
numbers1 = [5, 6, 2, 8]
numbers2 = [7, 1, 4, 9]
result = map(addition, numbers1, numbers2)
print(list(result))
# map 函数更加复杂的用法
def multiply(x):
    return (x*x)
def add(x):
    return (x+x)
func = [multiply, add]
for i in range(5):
    value = list(map(lambda x: x(i), func))
    print(value)
Explanation: map() 函数
python内建了 map() 和 reduce() 这两个功能强大的函数。
我们先看 map。map() 函数接收两个参数，一个是函数，一个是可迭代的序列，比如 list，map 将传入的函数依次作用到序列的每个元素，并把结果作为新的 Iterator 可迭代值返回。
举例说明，比如我们有一个函数 f(x) = x*x，要把这个函数作用在一个list [1, 2, 3, 4, 5, 6, 7, 8, 9]上，就可以用map()实现如下：
如果你知道 Google的那篇大名鼎鼎的论文“MapReduce: Simplified Data Processing on Large Clusters”，你就能大概明白map/reduce的概念。在 hadoop 时代，map/reduce 的理念是高效并行运算的核心。
End of explanation
# reduce 举例，一个加法函数
from functools import reduce
def add(x, y):
    return x + y
print(reduce(add, [1, 3, 5, 7, 9]))
# reduce，模拟一个字符串转换为整数的函数
from functools import reduce
def f(x, y):
    return x * 10 + y
def char2int(s):
    return {'0': 0, '1': 1, '2': 2, '3': 3, '4': 4, '5': 5, 
            '6': 6, '7': 7, '8': 8, '9': 9}[s]
def str2int(s):
    return reduce(f, map(char2int, s))
print(str2int('13579'))
print(type(str2int('13579')))
# 拆解上面的函数，先 map
list1 = map(char2int, '13579')
for i in list1:
    print(i,type(i))
# 拆解上面的函数，再 reduce
list1 = map(char2int, '13579')
print(reduce(f,list1))
Explanation: reduce() 函数
再看 reduce 的用法。reduce 把一个函数作用在一个序列[x1, x2, x3, ...]上，这个函数必须接收两个参数，reduce 把结果继续和序列的下一个元素做累积计算，其效果就是：
reduce(f, [x1, x2, x3, x4]) = f(f(f(x1, x2), x3), x4)
End of explanation
# filter 举例，在一个list中，删掉偶数，只保留奇数
# 判断是否是奇数
def is_odd(n):
    return n % 2 == 1
print(list(filter(is_odd, [1, 2, 4, 5, 6])))
# 筛选一个 list 中为空的元素
def is_empty(s):
    # strip() 用于移除字符串头尾指定的字符（默认为空格）
    if len(s.strip()) ==0:
        return False
    else:
        return True
print(list(filter(is_empty, ['A', '', 'B','C', '  '])))
# 返回一定范围内既不能被2整除也不能被3整数的数字
def f(x): 
    return x % 2 != 0 and x % 3 != 0
print(list(filter(f, range(2, 30))))
Explanation: filter() 函数
Python内建的filter()函数用于过滤序列。
和map()类似，filter()也接收一个函数和一个序列。和map()不同的是，filter()把传入的函数依次作用于每个元素，然后根据返回值是True还是False决定保留还是丢弃该元素。
End of explanation
<END_TASK>