全民一起玩Python提高篇第十四课:函数式编程初步(上)

函数与数字、字符串、列表等一样,本质上都是某种存放在内存中的数据类型,都可以用一个名字(变量名、函数名 …… )指向它
一个函数与一个数字、字符串等一样,都可以赋值给一个变量。比如,如果 f 是一个函数的名字,那么 g = f 就会让变量 g
也指向这个函数,从而使 g() 和 f() 执行同样的功能

my_fun()
#运行函数
my_fun
#找到函数内存地址和内容,但不运行

函数也可以去赋值
指向同一块内存

t=print
t('hello world!')
hello world!

根据这种原理,可以进行简单汉化

打印=print
求和=sum
长度=len
最大值=max
最小值=min
绝对值=abs
打印(3+2)
打印(最大值(4,长度('abcde')))
打印(求和([2,3,4,7]))

提高篇第十二课的一个案例

x=['博士','硕士','学士','圣斗士']
def degree_order(s):
    if s=='学士':return 1
    elif s=='硕士': return 2
    elif s == '博士':return 3
    elif s == '圣斗士':return 4
    else: return -1

print(sorted(x,key=degree_order))
#这里的key就是直接用函数来赋值
#指定字符映射为数字

类似的函数式编程思想

filter函数:

x=['abxdxxx','sad','wef','a','wqwewewq']
#使用filter函数,从列表中过滤数据
#把f函数作为一个参数,交给了另一个函数filter
def f(s):
    return len(s)<5

a=filter(f,x)
#把x中每个元素拿到f中去试试,返回True的留下
print(list(a))
y=['1231242','232','fdasfsd','ss']
print(list(filter(f,y)))

函数作为参数传参的情况,称为高阶函数

pi=3.1415926
print(round(pi,2))
#但如果都是要求保留两位,希望把这个2作为固定值
#可以先用 help(round)来查一下是否满足该用法
from functools import partial
#该包用来简化函数用法
round2=partial(round,ndigits=2)
#创造了新的函数round2
print(round2(pi))

题目:将函数赋值给变量

请完成以下实验操作并观察结果,体会把函数赋值给变量的语法。
定义一个函数my_fun,添加一个参数vals代表列表,该函数可以打印列表的所有元素值。
定义变量print_list,赋值为255,使用id()方法查看print_list的地址。
将my_fun赋值给print_list,使用id()方法查看my_fun与print_list的地址是否一样。
定义一个列表,通过print_list()打印列表的元素。

def my_func(vals):
    for i in vals:
        print(i)

print_list=255
print(id(print_list))
print_list=my_func
print(id(my_func))
print(id(print_list))
x=[1,2.3,4,2]
print_list(x)
8791395657312
5892416
5892416
1
2.3
4
2

题目:sorted函数练习

定义一个函数求绝对值,使用sorted函数将以下列表按照绝对值从小到大排序。
vals = [-7, 2, -3, -1, 5, 0, -0.3]
提示:对于求绝对值的函数,既可以使用Python标准库自带的 abs 函数,也可以自己编写一个。参考答案中为自己编写函数示例。

vals = [-7, 2, -3, -1, 5, 0, -0.3]
#def absolutely(s):
#    return abs(s)
def absolute(s):
    if s<=0:
        return -s
    else:
        return s
#可以自己写一个绝对值函数
print(sorted(vals,key=absolute))

题目:filter函数用法

以下列表中包含多个空格和None,请使用filter方法将其中的空白字符清除。
vals = [’ ', ‘Higher’, ‘Order’, None, ’ ', None, ‘Function’]

def Clear_None(s):
    if s and s.strip():
    #这里不能写成if s.strip() and s:
        return True
    else:
        return False

vals = ['  ', 'Higher', 'Order', None, ' ', None, 'Function']
print(list(filter(Clear_None,vals)))

题目:偏函数的用法

下面的二维列表中,每个元素(子列表)都有姓名与年龄两个数据。
students = [ [‘张三’,21], [‘李四’, 19], [‘王五’, 20], [‘赵六’, 17] ]
假如现在需要按照value(即每个人的年龄)排序:
那么使用 sorted 函数时,需要先编写一个自己的排序函数,比如:
def sort_by_age(item):
return item[1]
sorted(students, key=sort_by_age)
但是如果经常使用这种方式对类似列表排序,就会比较麻烦。因此请基于partial,编写一个专门对调用 sort_by_age 对列表排序的函数,名为 my_sorted。而该函数的特点是:只需传入一个参数,即列表名即可,例如:
my_sorted( students )

from functools import partial
students = [ ['张三',21], ['李四', 19], ['王五', 20], ['赵六', 17] ]
def sort_by_age(item):
    return item[1]

sort_age=partial(sorted,key=sort_by_age)
#利用偏函数固定住了key
print(sort_age(students))

题目:对象排序

使用 sorted + 自定义函数 的模式,不仅可以对普通类型(数字、字符串)等排序,而且还可以对任意自定义对象进行排序。
请先定义一个学生类,属性包括姓名和分数。
然后定义一个专门针对这种学生类对象的排序函数,接收一个学生类对象作为参数,然后将该学生对象的成绩返回,作为排序参考标准。
在主程序中创建多个学生类的对象,并存入一个列表。然后使用sorted函数,对该列表中的学生对象,按照自定义排序函数进行成绩排序。
最后将排好序的所有学生姓名和成绩,按顺序打印在屏幕上。

class stu:
    def __init__(self,name,grade):
        self.name=name
        self.grade=grade

def my_sort(stu):
    return stu.grade

if __name__=='__main__':
    student=[stu('锦到黑',379),stu('渣致命',382),stu('苦学宇',358)]
    result=sorted(student,key=my_sort)
    for i in result:
        print(i.name,i.grade)

map函数

对于操作如下的这种函数,先看两种常规做法

from math import *
a=[1,2,3,4,6,7]
b=[]
for i in a:
    r=sin(i)
    b.append(r)
c=[sin(i) for i in a]
#列表生成式的写法
print(b)
print(c)

利用这种思想,可以用map高阶函数,map(函数名,容器名),返回的是map类型的,可迭代,list转换即可

from math import *
a=[1,2,3,4,6,7]
b=map(sin,a)
print(list(b))
x=['尼','莫','锦到黑']
c=map(len,x)
print(list(c))

利用map可以简化代码量

from math import *
from functools import partial
a=[1,2,3,4,6,7]
f=partial(round,ndigits=2)
b=map(sin,a)
c=map(f,b)
print(list(c))
#简化写法
print(list(map(partial(round,ndigits=2),map(sin,a))))
#一行搞定

但c只是个迭代器,所以会出现这种情况

print(list(c))
print(list(c))
#c只是个迭代器,这样是用完就扔,不能重复使用
[0.84, 0.91, 0.14, -0.76, -0.28, 0.66]
[]

题目:map基本用法练习

请使用map函数代替for循环,将以下列表中的每个元素打印在屏幕上。
vals = [1, 3, 5, 7, 11, 13, 17, 19]

vals = [1, 3, 5, 7, 11, 13, 17, 19]
for i in vals:
    print(i)
#上下效果一样
list(map(print,vals))

题目:map调用自定义函数

请编写一个自定义函数,接收一个数字并返回其加一后的结果。比如接收 5 返回 6, 接收15 返回 16 。
然后使用 map 函数,调用该自定义函数,将以下列表中的数字都加一转换为偶数。
vals = [1, 3, 5, 7, 9, 11, 13, 15, 17]

def add_1(s):
    return s+1

vals=[1, 3, 5, 7, 9, 11, 13, 15, 17]
print(list(map(add_1,vals)))

题目:map处理字符串

请编写一个自定义函数,接收一个字符串(单词),然后使每个单词首字母大写,其他字母小写。
接下来使用map函数,对下面字符串中的每个单词(空格为分隔符)进行前述大小写处理,最后打印出转换后的整个新闻标题字符串。
news = ‘Aussie ciTy counCil Resumes Ties witH Chinese sister city’
提示:字符串的lower方法可以转换小写,capitalize方法可以使首字母大写。

def change_word(s):
    a=s.lower().capitalize()
    #统一转为小写,再把首字母大写
    return a

if __name__=='__main__':
    news = 'Aussie ciTy counCil Resumes Ties witH Chinese sister city'
    b=news.split(' ')
    #先拆分原串

    word=[]
    for i in b:
        word.append(change_word(i))
    s=' '.join(word)
    print(s)
    #上下的代码结果相同
    print(' '.join(list(map(change_word,b))))

题目:map函数嵌套

下面的二维列表中保存了三个班级的学员成绩。
scores = [
[87, 92, 88, 54, 62, 99, 71, 64],
[76, 81, 87, 53, 60, 68, 70, 63],
[94, 79, 75, 61, 48, 76, 84, 91]
]
请先编写一个自定义函数 avg ,接收一个列表为参数并返回列表中所有数字的平均数(平均数的格式为浮点数、不取整)。
然后使用嵌套 map 函数,要求最终得到一个列表,里面是各个班级的平均成绩,并且必须是整数。

scores = [ [87, 92, 88, 54, 62, 99, 71, 64],
                [76, 81, 87, 53, 60, 68, 70, 63],
                [94, 79, 75, 61, 48, 76, 84, 91] ]

def avg(s):
    ave=sum(s)/ len(s)
    return ave

print(list(map(int, map(avg, scores))))
#扫描二维列表,每次读出的是其子列表

题目:高阶函数综合练习

以下爬虫数据的二维列表中包含三个品牌的笔记本商品信息。每个商品都是一个由空格隔开的字符串,前半部分是不需要的符号和文字,例如“【稀缺现货】”、“【极速发货】”等,而后半部分则是需要的品名和价格,比如“联想小新:4499”等。
notebooks = [
[’【超品日】 联想小新:4499’, ‘联想拯救者:4998’, ‘【新品上市】 联想扬天:2499’],
[’【旗舰店】 戴尔灵越5000:4549’, ‘【稀缺现货】 戴尔新G3:5899’, ‘戴尔成就3000:4299’],
[‘惠普星系列青春版:2799’, ‘【新品上市】 惠普暗影精灵五代:5599’, ‘【极速发货】 惠普星14:2999’]
]
请使用map完成以下任务:

  1. 将列表中不需要的符号和文字清除,只保留“联想小新:4499”、“惠普暗影精灵五代:5599”等信息;
  2. 再编写一个自定义排序函数,接收一个商品信息字符串如 “联想小新:4499” ,然后返回冒号后面的价格数字作为排序依据。接下来再次应用 map ,并使用 sorted 和 partial等高阶函数,对上一步得到的商品列表按价格排序。
import re

notebooks = [ ['【超品日】 联想小新:4499', '联想拯救者:4998', '【新品上市】 联想扬天:2499'],
                        ['【旗舰店】 戴尔灵越5000:4549', '【稀缺现货】 戴尔新G3:5899', '戴尔成就3000:4299'],
                        ['惠普星系列青春版:2799', '【新品上市】 惠普暗影精灵五代:5599', '【极速发货】 惠普星14:2999'] ]
notebook=[]
for i in notebooks:
    for j in i:
        r = re.sub(r'【.+?】\s*', r'', j)
        notebook.append(r)
    # 用正则表达式替换来删除多余部分

def my_sort(s):
    return int(s.split(':',1)[1])

print(sorted(notebook,key=my_sort))
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值